dolibarr 21.0.0-beta
list.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2001-2006 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2019 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005-2012 Regis Houssin <regis.houssin@inodbox.com>
5 * Copyright (C) 2012-2016 Marcos García <marcosgdf@gmail.com>
6 * Copyright (C) 2013-2023 Juanjo Menent <jmenent@2byte.es>
7 * Copyright (C) 2013-2015 Raphaël Doursenaud <rdoursenaud@gpcsolutions.fr>
8 * Copyright (C) 2013 Jean Heimburger <jean@tiaris.info>
9 * Copyright (C) 2013 Cédric Salvador <csalvador@gpcsolutions.fr>
10 * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
11 * Copyright (C) 2013 Adolfo segura <adolfo.segura@gmail.com>
12 * Copyright (C) 2015 Jean-François Ferry <jfefe@aternatik.fr>
13 * Copyright (C) 2016 Ferran Marcet <fmarcet@2byte.es>
14 * Copyright (C) 2020-2021 Open-DSI <support@open-dsi.fr>
15 * Copyright (C) 2022 Charlene Benke <charlene@patas-monkey.com>
16 * Copyright (C) 2020-2023 Alexandre Spangaro <aspangaro@easya.solutions>
17 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
18 * Copyright (C) 2024 Benjamin Falière <benjamin.faliere@altairis.fr>
19 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
20 *
21 * This program is free software; you can redistribute it and/or modify
22 * it under the terms of the GNU General Public License as published by
23 * the Free Software Foundation; either version 3 of the License, or
24 * (at your option) any later version.
25 *
26 * This program is distributed in the hope that it will be useful,
27 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
29 * GNU General Public License for more details.
30 *
31 * You should have received a copy of the GNU General Public License
32 * along with this program. If not, see <https://www.gnu.org/licenses/>.
33 */
34
42// Load Dolibarr environment
43require '../main.inc.php';
44require_once DOL_DOCUMENT_ROOT.'/core/lib/accounting.lib.php';
45require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
46require_once DOL_DOCUMENT_ROOT.'/core/lib/product.lib.php';
47require_once DOL_DOCUMENT_ROOT.'/core/class/html.formcompany.class.php';
48require_once DOL_DOCUMENT_ROOT.'/core/class/html.formother.class.php';
49require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.product.class.php';
50require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
51require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
52
53if (isModEnabled('workstation')) {
54 require_once DOL_DOCUMENT_ROOT.'/workstation/class/workstation.class.php';
55}
56if (isModEnabled('category')) {
57 require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php';
58 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formcategory.class.php';
59}
60
70// Load translation files required by the page
71$langs->loadLangs(array('products', 'stocks', 'suppliers', 'companies', 'margins'));
72if (isModEnabled('productbatch')) {
73 $langs->load("productbatch");
74}
75
76
77// Get parameters
78$action = GETPOST('action', 'aZ09');
79$massaction = GETPOST('massaction', 'alpha');
80$show_files = GETPOSTINT('show_files');
81$confirm = GETPOST('confirm', 'alpha');
82$toselect = GETPOST('toselect', 'array');
83$optioncss = GETPOST('optioncss', 'alpha');
84$mode = GETPOST('mode', 'alpha');
85
86$fourn_id = GETPOSTINT("fourn_id");
87
88// Search Criteria
89$search_all = trim(GETPOST('search_all', 'alphanohtml'));
90$search_id = GETPOST("search_id", 'alpha');
91$search_ref = GETPOST("search_ref", 'alpha');
92$search_ref_supplier = GETPOST("search_ref_supplier", 'alpha');
93$search_barcode = GETPOST("search_barcode", 'alpha');
94$search_label = GETPOST("search_label", 'alpha');
95$search_default_workstation = GETPOST("search_default_workstation", 'alpha');
96$search_type = GETPOST("search_type", "int");
97$search_vatrate = GETPOST("search_vatrate", 'alpha');
98$searchCategoryProductOperator = 0;
99if (GETPOSTISSET('formfilteraction')) {
100 $searchCategoryProductOperator = GETPOSTINT('search_category_product_operator');
101} elseif (getDolGlobalString('MAIN_SEARCH_CAT_OR_BY_DEFAULT')) {
102 $searchCategoryProductOperator = getDolGlobalString('MAIN_SEARCH_CAT_OR_BY_DEFAULT');
103}
104$searchCategoryProductList = GETPOST('search_category_product_list', 'array');
105$catid = GETPOSTINT('catid');
106if (!empty($catid) && empty($searchCategoryProductList)) {
107 $searchCategoryProductList = array($catid);
108}
109$search_tosell = GETPOST("search_tosell");
110$search_tobuy = GETPOST("search_tobuy");
111$search_country = GETPOST("search_country", 'aZ09');
112$search_state = GETPOST("state_id", 'intcomma');
113$search_tobatch = GETPOST("search_tobatch");
114$search_accountancy_code_sell = GETPOST("search_accountancy_code_sell", 'alpha');
115$search_accountancy_code_sell_intra = GETPOST("search_accountancy_code_sell_intra", 'alpha');
116$search_accountancy_code_sell_export = GETPOST("search_accountancy_code_sell_export", 'alpha');
117$search_accountancy_code_buy = GETPOST("search_accountancy_code_buy", 'alpha');
118$search_accountancy_code_buy_intra = GETPOST("search_accountancy_code_buy_intra", 'alpha');
119$search_accountancy_code_buy_export = GETPOST("search_accountancy_code_buy_export", 'alpha');
120$search_import_key = GETPOST("search_import_key", 'alpha');
121$search_finished = GETPOST("search_finished");
122$search_units = GETPOST('search_units', 'int');
123$type = GETPOST("type", 'alpha');
124
125// Show/hide child product variants
126$show_childproducts = 0;
127if (isModEnabled('variants')) {
128 $show_childproducts = GETPOST('search_show_childproducts');
129}
130
131$diroutputmassaction = $conf->product->dir_output.'/temp/massgeneration/'.$user->id;
132
133// Load variable for pagination
134$limit = GETPOSTINT('limit') ? GETPOSTINT('limit') : $conf->liste_limit;
135$sortfield = GETPOST('sortfield', 'aZ09comma');
136$sortorder = GETPOST('sortorder', 'aZ09comma');
137$page = GETPOSTISSET('pageplusone') ? (GETPOSTINT('pageplusone') - 1) : GETPOSTINT("page");
138if (empty($page) || $page < 0 || GETPOST('button_search', 'alpha') || GETPOST('button_removefilter', 'alpha')) {
139 // If $page is not defined, or '' or -1 or if we click on clear filters
140 $page = 0;
141}
142$offset = $limit * $page;
143$pageprev = $page - 1;
144$pagenext = $page + 1;
145if (!$sortfield) {
146 $sortfield = "p.ref";
147}
148if (!$sortorder) {
149 $sortorder = "ASC";
150}
151
152// Initialize context for list
153$contextpage = GETPOST('contextpage', 'aZ') ? GETPOST('contextpage', 'aZ') : 'productservicelist';
154if ((string) $type == '1') {
155 $contextpage = 'servicelist';
156 if ($search_type == '') {
157 $search_type = '1';
158 }
159}
160if ((string) $type == '0') {
161 $contextpage = 'productlist';
162 if ($search_type == '') {
163 $search_type = '0';
164 }
165}
166
167// Initialize a technical object to manage hooks. Note that conf->hooks_modules contains array of hooks
168$object = new Product($db);
169$hookmanager->initHooks(array('productservicelist'));
170$extrafields = new ExtraFields($db);
171$form = new Form($db);
172$formcompany = new FormCompany($db);
173$formproduct = new FormProduct($db);
174
175// fetch optionals attributes and labels
176$extrafields->fetch_name_optionals_label($object->table_element);
177$search_array_options = $extrafields->getOptionalsFromPost($object->table_element, '', 'search_');
178
179if (empty($action)) {
180 $action = 'list';
181}
182
183// Get object canvas (By default, this is not defined, so standard usage of dolibarr)
184$canvas = GETPOST("canvas");
185$objcanvas = null;
186if (!empty($canvas)) {
187 require_once DOL_DOCUMENT_ROOT.'/core/class/canvas.class.php';
188 $objcanvas = new Canvas($db, $action);
189 $objcanvas->getCanvas('product', 'list', $canvas);
190}
191
192// Define virtualdiffersfromphysical
193$virtualdiffersfromphysical = 0;
194if (getDolGlobalString('STOCK_CALCULATE_ON_SHIPMENT')
195 || getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_DISPATCH_ORDER')
196 || getDolGlobalString('STOCK_CALCULATE_ON_SHIPMENT_CLOSE')
197 || getDolGlobalString('STOCK_CALCULATE_ON_RECEPTION')
198 || getDolGlobalString('STOCK_CALCULATE_ON_RECEPTION_CLOSE')
199 || isModEnabled('mrp')) {
200 $virtualdiffersfromphysical = 1; // According to increase/decrease stock options, virtual and physical stock may differs.
201}
202
203// List of fields to search into when doing a "search in all"
204$fieldstosearchall = array(
205 'p.ref' => "Ref",
206 'p.label' => "ProductLabel",
207 'p.description' => "Description",
208 "p.note" => "Note",
209 'pfp.ref_fourn' => 'RefSupplier'
210);
211// multilang
212if (getDolGlobalInt('MAIN_MULTILANGS')) {
213 $fieldstosearchall['pl.label'] = 'ProductLabelTranslated';
214 $fieldstosearchall['pl.description'] = 'ProductDescriptionTranslated';
215 $fieldstosearchall['pl.note'] = 'ProductNoteTranslated';
216}
217if (isModEnabled('barcode')) {
218 $fieldstosearchall['p.barcode'] = 'Gencod';
219 $fieldstosearchall['pfp.barcode'] = 'GencodBuyPrice';
220}
221// Personalized search criteria. Example: getDolGlobalString('PRODUCT_QUICKSEARCH_ON_FIELDS') = 'p.ref=ProductRef;p.label=ProductLabel;p.description=Description;p.note=Note;'
222if (getDolGlobalString('PRODUCT_QUICKSEARCH_ON_FIELDS')) {
223 $fieldstosearchall = dolExplodeIntoArray(getDolGlobalString('PRODUCT_QUICKSEARCH_ON_FIELDS'));
224}
225
226if (!getDolGlobalString('PRODUIT_MULTIPRICES')) {
227 $titlesellprice = $langs->trans("SellingPrice");
228 if (getDolGlobalString('PRODUIT_CUSTOMER_PRICES')) {
229 $titlesellprice = $form->textwithpicto($langs->trans("SellingPrice"), $langs->trans("DefaultPriceRealPriceMayDependOnCustomer"));
230 }
231}
232
233$isInEEC = isInEEC($mysoc);
234
235$alias_product_perentity = !getDolGlobalString('MAIN_PRODUCT_PERENTITY_SHARED') ? "p" : "ppe";
236
237$arraypricelevel = array();
238// Definition of array of fields for columns
239$arrayfields = array(
240 'p.rowid' => array('type' => 'integer', 'label' => 'TechnicalID', 'enabled' => 1, 'visible' => -2, 'noteditable' => 1, 'notnull' => 1, 'index' => 1, 'position' => 1, 'comment' => 'Id', 'css' => 'left'),
241 'p.ref' => array('label' => 'ProductRef', 'checked' => 1, 'position' => 10),
242 //'pfp.ref_fourn'=>array('label'=>$langs->trans("RefSupplier"), 'checked'=>1, 'enabled'=>(isModEnabled('barcode'))),
243 'thumbnail' => array('label' => 'Photo', 'checked' => 0, 'position' => 10),
244 'p.description' => array('label' => 'Description', 'checked' => 0, 'position' => 10),
245 'p.label' => array('label' => "Label", 'checked' => 1, 'position' => 10),
246 'p.fk_product_type' => array('label' => "Type", 'checked' => 0, 'enabled' => (isModEnabled("product") && isModEnabled("service")), 'position' => 11),
247 'p.barcode' => array('label' => "Gencod", 'checked' => 1, 'enabled' => (isModEnabled('barcode')), 'position' => 12),
248 'p.duration' => array('label' => "Duration", 'checked' => ($contextpage != 'productlist'), 'enabled' => (isModEnabled("service") && (string) $type == '1'), 'position' => 13),
249 'pac.fk_product_parent' => array('label' => "ParentProductOfVariant", 'checked' => -1, 'enabled' => (isModEnabled('variants')), 'position' => 14),
250 'p.finished' => array('label' => "Nature", 'checked' => 0, 'enabled' => (isModEnabled("product") && $type != '1'), 'position' => 19),
251 'p.weight' => array('label' => 'Weight', 'checked' => 0, 'enabled' => (isModEnabled("product") && $type != '1'), 'position' => 20),
252 'p.weight_units' => array('label' => 'WeightUnits', 'checked' => 0, 'enabled' => (isModEnabled("product") && $type != '1'), 'position' => 21),
253 'p.length' => array('label' => 'Length', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SIZE') && $type != '1'), 'position' => 22),
254 'p.length_units' => array('label' => 'LengthUnits', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SIZE') && $type != '1'), 'position' => 23),
255 'p.width' => array('label' => 'Width', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SIZE') && $type != '1'), 'position' => 24),
256 'p.width_units' => array('label' => 'WidthUnits', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SIZE') && $type != '1'), 'position' => 25),
257 'p.height' => array('label' => 'Height', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SIZE') && $type != '1'), 'position' => 26),
258 'p.height_units' => array('label' => 'HeightUnits', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SIZE') && $type != '1'), 'position' => 27),
259 'p.surface' => array('label' => 'Surface', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SURFACE') && $type != '1'), 'position' => 28),
260 'p.surface_units' => array('label' => 'SurfaceUnits', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_SURFACE') && $type != '1'), 'position' => 29),
261 'p.volume' => array('label' => 'Volume', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_VOLUME') && $type != '1'), 'position' => 30),
262 'p.volume_units' => array('label' => 'VolumeUnits', 'checked' => 0, 'enabled' => (isModEnabled("product") && !getDolGlobalString('PRODUCT_DISABLE_VOLUME') && $type != '1'), 'position' => 31),
263 'cu.label' => array('label' => "DefaultUnitToShow", 'checked' => 0, 'enabled' => (isModEnabled("product") && getDolGlobalString('PRODUCT_USE_UNITS')), 'position' => 32),
264 'p.fk_default_workstation' => array('label' => 'DefaultWorkstation', 'checked' => 0, 'enabled' => isModEnabled('workstation') && $type == 1, 'position' => 33),
265 'p.sellprice' => array('label' => "SellingPrice", 'checked' => 1, 'enabled' => !getDolGlobalString('PRODUIT_MULTIPRICES'), 'position' => 40),
266 'p.tva_tx' => array('label' => "VATRate", 'checked' => 0, 'enabled' => !getDolGlobalString('PRODUIT_MULTIPRICES'), 'position' => 41),
267 'p.minbuyprice' => array('label' => "BuyingPriceMinShort", 'checked' => 1, 'enabled' => ($user->hasRight('fournisseur', 'lire')), 'position' => 42),
268 'p.numbuyprice' => array('label' => "BuyingPriceNumShort", 'checked' => 0, 'enabled' => ($user->hasRight('fournisseur', 'lire')), 'position' => 43),
269 'p.pmp' => array('label' => "PMPValueShort", 'checked' => 0, 'enabled' => ($user->hasRight('fournisseur', 'lire')), 'position' => 44),
270 'p.cost_price' => array('label' => "CostPrice", 'checked' => 0, 'enabled' => ($user->hasRight('fournisseur', 'lire')), 'position' => 45),
271 'p.seuil_stock_alerte' => array('label' => "StockLimit", 'checked' => 0, 'enabled' => (isModEnabled('stock') && $user->hasRight('stock', 'lire') && ($contextpage != 'servicelist' || getDolGlobalString('STOCK_SUPPORTS_SERVICES'))), 'position' => 50),
272 'p.desiredstock' => array('label' => "DesiredStock", 'checked' => 1, 'enabled' => (isModEnabled('stock') && $user->hasRight('stock', 'lire') && ($contextpage != 'servicelist' || getDolGlobalString('STOCK_SUPPORTS_SERVICES'))), 'position' => 51),
273 'p.stock' => array('label' => "PhysicalStock", 'checked' => 1, 'enabled' => (isModEnabled('stock') && $user->hasRight('stock', 'lire') && ($contextpage != 'servicelist' || getDolGlobalString('STOCK_SUPPORTS_SERVICES'))), 'position' => 52),
274 'stock_virtual' => array('label' => "VirtualStock", 'checked' => 1, 'enabled' => (isModEnabled('stock') && $user->hasRight('stock', 'lire') && ($contextpage != 'servicelist' || getDolGlobalString('STOCK_SUPPORTS_SERVICES')) && $virtualdiffersfromphysical), 'position' => 53),
275 'p.tobatch' => array('label' => "ManageLotSerial", 'checked' => 0, 'enabled' => (isModEnabled('productbatch')), 'position' => 60),
276 'p.fk_country' => array('label' => "Country", 'checked' => 0, 'position' => 100),
277 'p.fk_state' => array('label' => "State", 'checked' => 0, 'position' => 101),
278 $alias_product_perentity . '.accountancy_code_sell' => array('label' => "ProductAccountancySellCode", 'checked' => 0, 'enabled' => !getDolGlobalString('PRODUCT_DISABLE_ACCOUNTING'), 'position' => 400),
279 $alias_product_perentity . '.accountancy_code_sell_intra' => array('label' => "ProductAccountancySellIntraCode", 'checked' => 0, 'enabled' => $isInEEC && !getDolGlobalString('PRODUCT_DISABLE_ACCOUNTING'), 'position' => 401),
280 $alias_product_perentity . '.accountancy_code_sell_export' => array('label' => "ProductAccountancySellExportCode", 'checked' => 0, 'enabled' => !getDolGlobalString('PRODUCT_DISABLE_ACCOUNTING'), 'position' => 402),
281 $alias_product_perentity . '.accountancy_code_buy' => array('label' => "ProductAccountancyBuyCode", 'checked' => 0, 'enabled' => !getDolGlobalString('PRODUCT_DISABLE_ACCOUNTING'), 'position' => 403),
282 $alias_product_perentity . '.accountancy_code_buy_intra' => array('label' => "ProductAccountancyBuyIntraCode", 'checked' => 0, 'enabled' => $isInEEC && !getDolGlobalString('PRODUCT_DISABLE_ACCOUNTING'), 'position' => 404),
283 $alias_product_perentity . '.accountancy_code_buy_export' => array('label' => "ProductAccountancyBuyExportCode", 'checked' => 0, 'enabled' => !getDolGlobalString('PRODUCT_DISABLE_ACCOUNTING'), 'position' => 405),
284 'p.datec' => array('label' => "DateCreation", 'checked' => 0, 'position' => 500),
285 'p.tms' => array('label' => "DateModificationShort", 'checked' => 0, 'position' => 500),
286 'p.tosell' => array('label' => $langs->transnoentitiesnoconv("Status").' ('.$langs->transnoentitiesnoconv("Sell").')', 'checked' => 1, 'position' => 1000),
287 'p.tobuy' => array('label' => $langs->transnoentitiesnoconv("Status").' ('.$langs->transnoentitiesnoconv("Buy").')', 'checked' => 1, 'position' => 1000),
288 'p.import_key' => array('type' => 'varchar(14)', 'label' => 'ImportId', 'enabled' => 1, 'visible' => -2, 'notnull' => -1, 'index' => 0, 'checked' => -1, 'position' => 1100),
289);
290/*foreach ($object->fields as $key => $val) {
291 // If $val['visible']==0, then we never show the field
292 if (!empty($val['visible'])) {
293 $visible = dol_eval($val['visible'], 1, 1, '1');
294 $arrayfields['p.'.$key] = array(
295 'label'=>$val['label'],
296 'checked'=>(($visible < 0) ? 0 : 1),
297 'enabled'=>(abs($visible) != 3 && (bool) dol_eval($val['enabled'], 1)),
298 'position'=>$val['position']
299 );
300 }
301}*/
302
303
304// MultiPrices
305if (getDolGlobalString('PRODUIT_MULTIPRICES')) {
306 $produit_multiprices_limit = getDolGlobalInt('PRODUIT_MULTIPRICES_LIMIT');
307 for ($i = 1; $i <= $produit_multiprices_limit; $i++) {
308 $keyforlabel = 'PRODUIT_MULTIPRICES_LABEL'.$i;
309 if (getDolGlobalString($keyforlabel)) {
310 $labelp = $i.' - '.$langs->transnoentitiesnoconv(getDolGlobalString($keyforlabel));
311 } else {
312 $labelp = $langs->transnoentitiesnoconv("SellingPrice")." ".$i;
313 }
314 $arrayfields['p.sellprice'.$i] = array('label' => $labelp, 'checked' => ($i == 1 ? 1 : 0), 'enabled' => getDolGlobalString('PRODUIT_MULTIPRICES'), 'position' => (float) ('40.'.sprintf('%03d', $i)));
315 $arraypricelevel[$i] = array($i);
316 }
317}
318
319// Extra fields
320include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_array_fields.tpl.php';
321
322$object->fields = dol_sort_array($object->fields, 'position');
323$arrayfields = dol_sort_array($arrayfields, 'position');
324'@phan-var-force array<string,array{label:string,checked?:int<0,1>,position?:int,help?:string}> $arrayfields'; // dol_sort_array looses type for Phan
325
326// Security check
327if ($search_type == '0') {
328 $result = restrictedArea($user, 'produit', '', '', '', '', '', 0);
329} elseif ($search_type == '1') {
330 $result = restrictedArea($user, 'service', '', '', '', '', '', 0);
331} else {
332 $result = restrictedArea($user, 'produit|service', '', '', '', '', '', 0);
333}
334
335
336/*
337 * Actions
338 */
339$error = 0;
340
341if (GETPOST('cancel', 'alpha')) {
342 $action = 'list';
343 $massaction = '';
344}
345if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
346 $massaction = '';
347}
348$parameters = array('arrayfields' => &$arrayfields);
349$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
350if ($reshook < 0) {
351 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
352}
353
354$rightskey = 'produit';
355if ($type == Product::TYPE_SERVICE) {
356 $rightskey = 'service';
357}
358
359if (empty($reshook)) {
360 // Selection of new fields
361 include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
362
363 // Purge search criteria
364 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')) { // All tests are required to be compatible with all browsers
365 $search_all = "";
366 $search_id = '';
367 $search_ref = "";
368 $search_ref_supplier = "";
369 $search_label = "";
370 $search_default_workstation = "";
371 $search_barcode = "";
372 $searchCategoryProductOperator = 0;
373 $searchCategoryProductList = array();
374 $search_tosell = "";
375 $search_tobuy = "";
376 $search_tobatch = '';
377 $search_country = "";
378 $search_state = "";
379 $search_vatrate = "";
380 $search_finished = '';
381 //$search_type=''; // There is 2 types of list: a list of product and a list of services. No list with both. So when we clear search criteria, we must keep the filter on type.
382
383 $show_childproducts = '';
384 $search_import_key = '';
385 $search_accountancy_code_sell = '';
386 $search_accountancy_code_sell_intra = '';
387 $search_accountancy_code_sell_export = '';
388 $search_accountancy_code_buy = '';
389 $search_accountancy_code_buy_intra = '';
390 $search_accountancy_code_buy_export = '';
391 $search_array_options = array();
392 $search_units = '';
393 }
394
395 // Mass actions
396 $objectclass = 'Product';
397 if ((string) $search_type == '1') {
398 $objectlabel = 'Services';
399 }
400 if ((string) $search_type == '0') {
401 $objectlabel = 'Products';
402 }
403
404 $permissiontoread = $user->hasRight($rightskey, 'lire');
405 $permissiontodelete = $user->hasRight($rightskey, 'supprimer');
406 $permissiontoadd = $user->hasRight($rightskey, 'creer');
407 $uploaddir = $conf->product->dir_output;
408 include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';
409
410 if ($massaction == 'switchonsalestatus' && $permissiontoadd) {
411 $product = new Product($db);
412 foreach ($toselect as $toselectid) {
413 $result = $product->fetch($toselectid);
414 if ($result > 0 && $product->id > 0) {
415 if ($product->setStatut($product->status ? 0 : 1, null, 'product', 'PRODUCT_MODIFY', 'tosell') < 0) {
416 setEventMessages($product->error, $product->errors, 'errors');
417 }
418 }
419 }
420 }
421 if ($massaction == 'switchonpurchasestatus' && $permissiontoadd) {
422 $product = new Product($db);
423 foreach ($toselect as $toselectid) {
424 $result = $product->fetch($toselectid);
425 if ($result > 0 && $product->id > 0) {
426 if ($product->setStatut($product->status_buy ? 0 : 1, null, 'product', 'PRODUCT_MODIFY', 'tobuy') < 0) {
427 setEventMessages($product->error, $product->errors, 'errors');
428 }
429 }
430 }
431 }
432}
433
434
435/*
436 * View
437 */
438
439$product_static = new Product($db);
440if (isModEnabled('workstation')) {
441 $workstation_static = new Workstation($db);
442}
443$product_fourn = new ProductFournisseur($db);
444
445$title = $langs->trans("ProductsAndServices");
446
447if ($search_type != '' && $search_type != '-1') {
448 if ($search_type == 1) {
449 $title = $langs->trans("Services");
450 } else {
451 $title = $langs->trans("Products");
452 }
453}
454
455// Build and execute select
456// --------------------------------------------------------------------
457$sql = 'SELECT p.rowid, p.ref, p.description, p.label, p.fk_product_type, p.barcode, p.price, p.tva_tx, p.price_ttc, p.price_base_type, p.entity,';
458$sql .= ' p.fk_product_type, p.duration, p.finished, p.tosell, p.tobuy, p.seuil_stock_alerte, p.desiredstock,';
459$sql .= ' p.tobatch, ';
460if (isModEnabled('workstation')) {
461 $sql .= ' p.fk_default_workstation, ws.status as status_workstation, ws.ref as ref_workstation, ';
462}
463if (!getDolGlobalString('MAIN_PRODUCT_PERENTITY_SHARED')) {
464 $sql .= " p.accountancy_code_sell, p.accountancy_code_sell_intra, p.accountancy_code_sell_export, p.accountancy_code_buy, p.accountancy_code_buy_intra, p.accountancy_code_buy_export,";
465} else {
466 $sql .= " ppe.accountancy_code_sell, ppe.accountancy_code_sell_intra, ppe.accountancy_code_sell_export, ppe.accountancy_code_buy, ppe.accountancy_code_buy_intra, ppe.accountancy_code_buy_export,";
467}
468$sql .= ' p.datec as date_creation, p.tms as date_modification, p.pmp, p.stock, p.cost_price,';
469$sql .= ' p.weight, p.weight_units, p.length, p.length_units, p.width, p.width_units, p.height, p.height_units, p.surface, p.surface_units, p.volume, p.volume_units,';
470$sql .= ' p.fk_country, p.fk_state,';
471$sql .= ' p.import_key,';
472if (getDolGlobalString('PRODUCT_USE_UNITS')) {
473 $sql .= ' p.fk_unit, cu.label as cu_label,';
474}
475$sql .= ' MIN(pfp.unitprice) as bestpurchaseprice';
476if (isModEnabled('variants')) {
477 $sql .= ', pac.rowid as prod_comb_id';
478 $sql .= ', pac.fk_product_parent';
479}
480// Add fields from extrafields
481if (!empty($extrafields->attributes[$object->table_element]['label'])) {
482 foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
483 $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? ", ef.".$key." as options_".$key : '');
484 }
485}
486// Add fields from hooks
487$parameters = array();
488$reshook = $hookmanager->executeHooks('printFieldListSelect', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
489$sql .= $hookmanager->resPrint;
490$sql = preg_replace('/,\s*$/', '', $sql);
491
492$sqlfields = $sql; // $sql fields to remove for count total
493
494$sql .= ' FROM '.MAIN_DB_PREFIX.'product as p';
495if (isModEnabled('workstation')) {
496 $sql .= " LEFT JOIN " . MAIN_DB_PREFIX . "workstation_workstation as ws ON (p.fk_default_workstation = ws.rowid)";
497}
498if (getDolGlobalString('MAIN_PRODUCT_PERENTITY_SHARED')) {
499 $sql .= " LEFT JOIN " . MAIN_DB_PREFIX . "product_perentity as ppe ON ppe.fk_product = p.rowid AND ppe.entity = " . ((int) $conf->entity);
500}
501if (!empty($extrafields->attributes[$object->table_element]['label']) && is_array($extrafields->attributes[$object->table_element]['label']) && count($extrafields->attributes[$object->table_element]['label'])) {
502 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product_extrafields as ef on (p.rowid = ef.fk_object)";
503}
504$linktopfp = " LEFT JOIN ".MAIN_DB_PREFIX."product_fournisseur_price as pfp ON p.rowid = pfp.fk_product";
505$sql .= $linktopfp;
506// multilang
507if (getDolGlobalInt('MAIN_MULTILANGS')) {
508 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product_lang as pl ON pl.fk_product = p.rowid AND pl.lang = '".$db->escape($langs->getDefaultLang())."'";
509}
510if (isModEnabled('variants')) {
511 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product_attribute_combination pac ON pac.fk_product_child = p.rowid";
512}
513if (getDolGlobalString('PRODUCT_USE_UNITS')) {
514 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."c_units cu ON cu.rowid = p.fk_unit";
515}
516
517// Add table from hooks
518$parameters = array();
519$reshook = $hookmanager->executeHooks('printFieldListFrom', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
520$sql .= $hookmanager->resPrint;
521
522$sql .= ' WHERE p.entity IN ('.getEntity('product').')';
523if ($search_all) {
524 // Clean $fieldstosearchall
525 $newfieldstosearchall = $fieldstosearchall;
526 unset($newfieldstosearchall['pfp.ref_fourn']);
527 unset($newfieldstosearchall['pfp.barcode']);
528
529 $sql .= ' AND (';
530 $sql .= natural_search(array_keys($newfieldstosearchall), $search_all, 0, 1);
531 // Search also into a supplier reference 'pfp.ref_fourn'="RefSupplier"
532 $sql .= ' OR EXISTS (SELECT rowid FROM '.MAIN_DB_PREFIX.'product_fournisseur_price as pfp WHERE pfp.fk_product = p.rowid';
533 $sql .= ' AND ('.natural_search('pfp.ref_fourn', $search_all, 0, 1);
534 if (isModEnabled('barcode')) {
535 // Search also into a supplier barcode 'pfp.barcode'='GencodBuyPrice';
536 $sql .= ' OR '.natural_search('pfp.barcode', $search_all, 0, 1);
537 }
538 $sql .= ')))';
539}
540// if the type is not 1, we show all products (type = 0,2,3)
541if (dol_strlen($search_type) && $search_type != '-1') {
542 if ($search_type == 1) {
543 $sql .= " AND p.fk_product_type = 1";
544 } else {
545 $sql .= " AND p.fk_product_type <> 1";
546 }
547}
548
549if (isModEnabled('variants') && !$show_childproducts) {
550 $sql .= " AND pac.rowid IS NULL";
551}
552
553if ($search_id) {
554 $sql .= natural_search('p.rowid', $search_id, 1);
555}
556if ($search_ref) {
557 $sql .= natural_search('p.ref', $search_ref);
558}
559if ($search_label) {
560 $sql .= natural_search('p.label', $search_label);
561}
562if ($search_default_workstation) {
563 $sql .= natural_search('ws.ref', $search_default_workstation);
564}
565if ($search_barcode) {
566 $sql .= natural_search('p.barcode', $search_barcode);
567}
568if ($search_import_key) {
569 $sql .= natural_search('p.import_key', $search_import_key);
570}
571if (isset($search_tosell) && dol_strlen($search_tosell) > 0 && $search_tosell != -1) {
572 $sql .= " AND p.tosell = ".((int) $search_tosell);
573}
574if (isset($search_tobuy) && dol_strlen($search_tobuy) > 0 && $search_tobuy != -1) {
575 $sql .= " AND p.tobuy = ".((int) $search_tobuy);
576}
577if (isset($search_tobatch) && dol_strlen($search_tobatch) > 0 && $search_tobatch != -1) {
578 $sql .= " AND p.tobatch = ".((int) $search_tobatch);
579}
580if ($search_vatrate) {
581 $sql .= natural_search('p.tva_tx', $search_vatrate, 1);
582}
583if (dol_strlen($canvas) > 0) {
584 $sql .= " AND p.canvas = '".$db->escape($canvas)."'";
585}
586
587// Search for tag/category ($searchCategoryProductList is an array of ID)
588if (!empty($searchCategoryProductList)) {
589 $searchCategoryProductSqlList = array();
590 $listofcategoryid = '';
591 foreach ($searchCategoryProductList as $searchCategoryProduct) {
592 if (intval($searchCategoryProduct) == -2) {
593 $searchCategoryProductSqlList[] = "NOT EXISTS (SELECT ck.fk_product FROM ".MAIN_DB_PREFIX."categorie_product as ck WHERE p.rowid = ck.fk_product)";
594 } elseif (intval($searchCategoryProduct) > 0) {
595 if ($searchCategoryProductOperator == 0) {
596 $searchCategoryProductSqlList[] = " EXISTS (SELECT ck.fk_product FROM ".MAIN_DB_PREFIX."categorie_product as ck WHERE p.rowid = ck.fk_product AND ck.fk_categorie = ".((int) $searchCategoryProduct).")";
597 } else {
598 $listofcategoryid .= ($listofcategoryid ? ', ' : '') .((int) $searchCategoryProduct);
599 }
600 }
601 }
602 if ($listofcategoryid) {
603 $searchCategoryProductSqlList[] = " EXISTS (SELECT ck.fk_product FROM ".MAIN_DB_PREFIX."categorie_product as ck WHERE p.rowid = ck.fk_product AND ck.fk_categorie IN (".$db->sanitize($listofcategoryid)."))";
604 }
605 if ($searchCategoryProductOperator == 1) {
606 if (!empty($searchCategoryProductSqlList)) {
607 $sql .= " AND (".implode(' OR ', $searchCategoryProductSqlList).")";
608 }
609 } else {
610 if (!empty($searchCategoryProductSqlList)) {
611 $sql .= " AND (".implode(' AND ', $searchCategoryProductSqlList).")";
612 }
613 }
614}
615if ($fourn_id > 0) {
616 $sql .= " AND pfp.fk_soc = ".((int) $fourn_id);
617}
618if ($search_country) {
619 $sql .= " AND p.fk_country = ".((int) $search_country);
620}
621if ($search_state) {
622 $sql .= " AND p.fk_state = ".((int) $search_state);
623}
624if ($search_finished >= 0 && $search_finished !== '') {
625 $sql .= " AND p.finished = ".((int) $search_finished);
626}
627if ($search_accountancy_code_sell) {
628 $sql .= natural_search($alias_product_perentity . '.accountancy_code_sell', clean_account($search_accountancy_code_sell));
629}
630if ($search_accountancy_code_sell_intra) {
631 $sql .= natural_search($alias_product_perentity . '.accountancy_code_sell_intra', clean_account($search_accountancy_code_sell_intra));
632}
633if ($search_accountancy_code_sell_export) {
634 $sql .= natural_search($alias_product_perentity . '.accountancy_code_sell_export', clean_account($search_accountancy_code_sell_export));
635}
636if ($search_accountancy_code_buy) {
637 $sql .= natural_search($alias_product_perentity . '.accountancy_code_buy', clean_account($search_accountancy_code_buy));
638}
639if ($search_accountancy_code_buy_intra) {
640 $sql .= natural_search($alias_product_perentity . '.accountancy_code_buy_intra', clean_account($search_accountancy_code_buy_intra));
641}
642if ($search_accountancy_code_buy_export) {
643 $sql .= natural_search($alias_product_perentity . '.accountancy_code_buy_export', clean_account($search_accountancy_code_buy_export));
644}
645if (getDolGlobalString('PRODUCT_USE_UNITS') && $search_units && $search_units != '-1') {
646 $sql .= natural_search('cu.rowid', $search_units);
647}
648
649// Add where from extra fields
650include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_sql.tpl.php';
651// Add where from hooks
652$parameters = array();
653$reshook = $hookmanager->executeHooks('printFieldListWhere', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
654$sql .= $hookmanager->resPrint;
655$sql .= " GROUP BY p.rowid, p.ref, p.description, p.label, p.barcode, p.price, p.tva_tx, p.price_ttc, p.price_base_type,";
656$sql .= " p.fk_product_type, p.duration, p.finished, p.tosell, p.tobuy, p.seuil_stock_alerte, p.desiredstock,";
657$sql .= ' p.datec, p.tms, p.entity, p.tobatch, p.pmp, p.cost_price, p.stock,';
658if (!getDolGlobalString('MAIN_PRODUCT_PERENTITY_SHARED')) {
659 $sql .= " p.accountancy_code_sell, p.accountancy_code_sell_intra, p.accountancy_code_sell_export, p.accountancy_code_buy, p.accountancy_code_buy_intra, p.accountancy_code_buy_export,";
660} else {
661 $sql .= " ppe.accountancy_code_sell, ppe.accountancy_code_sell_intra, ppe.accountancy_code_sell_export, ppe.accountancy_code_buy, ppe.accountancy_code_buy_intra, ppe.accountancy_code_buy_export,";
662}
663$sql .= ' p.weight, p.weight_units, p.length, p.length_units, p.width, p.width_units, p.height, p.height_units, p.surface, p.surface_units, p.volume, p.volume_units,';
664$sql .= ' p.fk_country, p.fk_state,';
665$sql .= ' p.import_key';
666if (getDolGlobalString('PRODUCT_USE_UNITS')) {
667 $sql .= ', p.fk_unit, cu.label';
668}
669if (isModEnabled('workstation')) {
670 $sql .= ', p.fk_default_workstation, ws.status, ws.ref';
671}
672if (isModEnabled('variants')) {
673 $sql .= ', pac.rowid';
674 $sql .= ', pac.fk_product_parent';
675}
676// Add fields from extrafields
677if (!empty($extrafields->attributes[$object->table_element]['label'])) {
678 foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
679 $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? ", ef.".$key : '');
680 }
681}
682// Add groupby from hooks
683$parameters = array();
684$reshook = $hookmanager->executeHooks('printFieldListGroupBy', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
685$sql .= $hookmanager->resPrint;
686//if (GETPOST("toolowstock")) $sql.= " HAVING SUM(s.reel) < p.seuil_stock_alerte"; // Not used yet
687
688$nbtotalofrecords = '';
689if (!getDolGlobalInt('MAIN_DISABLE_FULL_SCANLIST')) {
690 /* The fast and low memory method to get and count full list converts the sql into a sql count */
691 $sqlforcount = preg_replace('/^'.preg_quote($sqlfields, '/').'/', 'SELECT COUNT(*) as nbtotalofrecords', $sql);
692 $sqlforcount = preg_replace('/'.preg_quote($linktopfp, '/').'/', '', $sqlforcount);
693 $sqlforcount = preg_replace('/GROUP BY .*$/', '', $sqlforcount);
694
695 $resql = $db->query($sqlforcount);
696 if ($resql) {
697 $objforcount = $db->fetch_object($resql);
698 $nbtotalofrecords = $objforcount->nbtotalofrecords;
699 } else {
700 dol_print_error($db);
701 }
702
703 if (($page * $limit) > $nbtotalofrecords) { // if total resultset is smaller than the paging size (filtering), goto and load page 0
704 $page = 0;
705 $offset = 0;
706 }
707 $db->free($resql);
708}
709
710// Complete request and execute it with limit
711$sql .= $db->order($sortfield, $sortorder);
712if ($limit) {
713 $sql .= $db->plimit($limit + 1, $offset);
714}
715
716$resql = $db->query($sql);
717if (!$resql) {
718 dol_print_error($db);
719 exit;
720}
721
722$num = $db->num_rows($resql);
723
724
725// Direct jump if only one record found
726if ($num == 1 && getDolGlobalString('MAIN_SEARCH_DIRECT_OPEN_IF_ONLY_ONE') && $search_all) {
727 $obj = $db->fetch_object($resql);
728 $id = $obj->rowid;
729 header("Location: ".DOL_URL_ROOT.'/product/card.php?id='.$id);
730 exit;
731}
732
733
734// Output page
735// --------------------------------------------------------------------
736
737$helpurl = '';
738if ($search_type != '') {
739 if ($search_type == 0) {
740 $helpurl = 'EN:Module_Products|FR:Module_Produits|ES:M&oacute;dulo_Productos';
741 } elseif ($search_type == 1) {
742 $helpurl = 'EN:Module_Services_En|FR:Module_Services|ES:M&oacute;dulo_Servicios';
743 }
744}
745
746$paramsCat = '';
747foreach ($searchCategoryProductList as $searchCategoryProduct) {
748 $paramsCat .= "&search_category_product_list[]=".urlencode($searchCategoryProduct);
749}
750
751//llxHeader('', $title, $helpurl, '', 0, 0, array(), array(), $paramsCat, 'classforhorizontalscrolloftabs');
752llxHeader('', $title, $helpurl, '', 0, 0, array(), array(), $paramsCat, 'bodyforlist mod-product page-list');
753
754$arrayofselected = is_array($toselect) ? $toselect : array();
755
756// Displays product removal confirmation
757if (GETPOST('delprod')) {
758 setEventMessages($langs->trans("ProductDeleted", GETPOST('delprod')), null, 'mesgs');
759}
760
761$param = '';
762if (!empty($mode)) {
763 $param .= '&mode='.urlencode($mode);
764}
765if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
766 $param .= '&contextpage='.urlencode($contextpage);
767}
768if ($limit > 0 && $limit != $conf->liste_limit) {
769 $param .= '&limit='.((int) $limit);
770}
771if ($optioncss != '') {
772 $param .= '&optioncss='.urlencode($optioncss);
773}
774if ($search_all) {
775 $param .= "&search_all=".urlencode($search_all);
776}
777if ($searchCategoryProductOperator == 1) {
778 $param .= "&search_category_product_operator=".urlencode((string) ($searchCategoryProductOperator));
779}
780foreach ($searchCategoryProductList as $searchCategoryProduct) {
781 $param .= "&search_category_product_list[]=".urlencode($searchCategoryProduct);
782}
783if ($search_ref) {
784 $param .= "&search_ref=".urlencode($search_ref);
785}
786if ($search_ref_supplier) {
787 $param .= "&search_ref_supplier=".urlencode($search_ref_supplier);
788}
789if ($search_barcode) {
790 $param .= ($search_barcode ? "&search_barcode=".urlencode($search_barcode) : "");
791}
792if ($search_import_key) {
793 $param .= "&search_import_key=".urlencode($search_import_key);
794}
795if ($search_label) {
796 $param .= "&search_label=".urlencode($search_label);
797}
798if ($search_default_workstation) {
799 $param .= "&search_default_workstation=".urlencode($search_default_workstation);
800}
801if ($search_tosell != '') {
802 $param .= "&search_tosell=".urlencode($search_tosell);
803}
804if ($search_tobuy != '') {
805 $param .= "&search_tobuy=".urlencode($search_tobuy);
806}
807if ($search_tobatch) {
808 $param .= "&search_tobatch=".urlencode($search_tobatch);
809}
810if ($search_country != '') {
811 $param .= "&search_country=".urlencode((string) ($search_country));
812}
813if ($search_state != '') {
814 $param .= "&search_state=".urlencode((string) ($search_state));
815}
816if ($search_vatrate) {
817 $param .= "&search_vatrate=".urlencode($search_vatrate);
818}
819if ($fourn_id > 0) {
820 $param .= "&fourn_id=".urlencode((string) ($fourn_id));
821}
822if ($show_childproducts) {
823 $param .= ($show_childproducts ? "&search_show_childproducts=".urlencode($show_childproducts) : "");
824}
825if ($type != '') {
826 $param .= '&type='.urlencode((string) ($type));
827}
828if ($search_type != '') {
829 $param .= '&search_type='.urlencode($search_type);
830}
831if ($search_accountancy_code_sell) {
832 $param .= "&search_accountancy_code_sell=".urlencode($search_accountancy_code_sell);
833}
834if ($search_accountancy_code_sell_intra) {
835 $param .= "&search_accountancy_code_sell_intra=".urlencode($search_accountancy_code_sell_intra);
836}
837if ($search_accountancy_code_sell_export) {
838 $param .= "&search_accountancy_code_sell_export=".urlencode($search_accountancy_code_sell_export);
839}
840if ($search_accountancy_code_buy) {
841 $param .= "&search_accountancy_code_buy=".urlencode($search_accountancy_code_buy);
842}
843if ($search_accountancy_code_buy_intra) {
844 $param .= "&search_accountancy_code_buy_intra=".urlencode($search_accountancy_code_buy_intra);
845}
846if ($search_accountancy_code_buy_export) {
847 $param .= "&search_accountancy_code_buy_export=".urlencode($search_accountancy_code_buy_export);
848}
849if ($search_finished) {
850 $param .= "&search_finished=".urlencode($search_finished);
851}
852// Add $param from extra fields
853include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
854
855// Add $param from hooks
856$parameters = array('param' => &$param);
857$reshook = $hookmanager->executeHooks('printFieldListSearchParam', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
858$param .= $hookmanager->resPrint;
859
860// List of mass actions available
861$arrayofmassactions = array(
862 'generate_doc' => img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("ReGeneratePDF"),
863 'edit_extrafields' => img_picto('', 'edit', 'class="pictofixedwidth"').$langs->trans("ModifyValueExtrafields"),
864 //'builddoc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("PDFMerge"),
865 //'presend'=>img_picto('', 'email', 'class="pictofixedwidth"').$langs->trans("SendByMail"),
866);
867if ($user->hasRight($rightskey, 'creer')) {
868 $arrayofmassactions['preupdateprice'] = img_picto('', 'edit', 'class="pictofixedwidth"').$langs->trans("UpdatePrice");
869 $arrayofmassactions['switchonsalestatus'] = img_picto('', 'stop-circle', 'class="pictofixedwidth"').$langs->trans("SwitchOnSaleStatus");
870 $arrayofmassactions['switchonpurchasestatus'] = img_picto('', 'stop-circle', 'class="pictofixedwidth"').$langs->trans("SwitchOnPurchaseStatus");
871}
872if (isModEnabled('category') && $user->hasRight($rightskey, 'creer')) {
873 $arrayofmassactions['preaffecttag'] = img_picto('', 'category', 'class="pictofixedwidth"').$langs->trans("AffectTag");
874}
875if (in_array($massaction, array('presend', 'predelete','preaffecttag', 'edit_extrafields', 'preupdateprice'))) {
876 $arrayofmassactions = array();
877}
878if ($user->hasRight($rightskey, 'supprimer')) {
879 $arrayofmassactions['predelete'] = img_picto('', 'delete', 'class="pictofixedwidth"').$langs->trans("Delete");
880}
881$massactionbutton = $form->selectMassAction('', $arrayofmassactions);
882
883$newcardbutton = '';
884$newcardbutton .= dolGetButtonTitle($langs->trans('ViewList'), '', 'fa fa-bars imgforviewmode', $_SERVER["PHP_SELF"].'?mode=common'.preg_replace('/(&|\?)*mode=[^&]+/', '', $param), '', ((empty($mode) || $mode == 'common') ? 2 : 1), array('morecss' => 'reposition'));
885$newcardbutton .= dolGetButtonTitle($langs->trans('ViewKanban'), '', 'fa fa-th-list imgforviewmode', $_SERVER["PHP_SELF"].'?mode=kanban'.preg_replace('/(&|\?)*mode=[^&]+/', '', $param), '', ($mode == 'kanban' ? 2 : 1), array('morecss' => 'reposition'));
886
887if ($type === "") {
888 $perm = ($user->hasRight('produit', 'creer') || $user->hasRight('service', 'creer'));
889} elseif ($type == Product::TYPE_SERVICE) {
890 $perm = $user->hasRight('service', 'creer');
891} elseif ($type == Product::TYPE_PRODUCT) {
892 $perm = $user->hasRight('produit', 'creer');
893}
894$oldtype = $type;
895$params = array();
896if ($type === "") {
897 $params['forcenohideoftext'] = 1;
898}
899$newcardbutton .= dolGetButtonTitleSeparator();
900if ((isModEnabled('product') && $type === "") || $type == Product::TYPE_PRODUCT) {
901 $label = 'NewProduct';
902 $newcardbutton .= dolGetButtonTitle($langs->trans($label), '', 'fa fa-plus-circle', DOL_URL_ROOT.'/product/card.php?action=create&type=0', '', $perm, $params);
903}
904if ((isModEnabled('service') && $type === "") || $type == Product::TYPE_SERVICE) {
905 $label = 'NewService';
906 $newcardbutton .= dolGetButtonTitle($langs->trans($label), '', 'fa fa-plus-circle', DOL_URL_ROOT.'/product/card.php?action=create&type=1', '', $perm, $params);
907}
908
909print '<form id="searchFormList" action="'.$_SERVER["PHP_SELF"].'" method="POST" name="formulaire">';
910if ($optioncss != '') {
911 print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
912}
913print '<input type="hidden" name="token" value="'.newToken().'">';
914print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
915print '<input type="hidden" name="action" value="list">';
916print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
917print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
918//print '<input type="hidden" name="page" value="'.$page.'">';
919print '<input type="hidden" name="type" value="'.$type.'">';
920print '<input type="hidden" name="page_y" value="">';
921print '<input type="hidden" name="mode" value="'.$mode.'">';
922
923if (empty($arrayfields['p.fk_product_type']['checked'])) {
924 print '<input type="hidden" name="search_type" value="'.dol_escape_htmltag($search_type).'">';
925}
926
927$picto = 'product';
928if ($type == 1) {
929 $picto = 'service';
930}
931
932print_barre_liste($title, $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, $picto, 0, $newcardbutton, '', $limit, 0, 0, 1);
933
934$topicmail = "Information";
935$modelmail = "product";
936$objecttmp = new Product($db);
937$trackid = 'prod'.$object->id;
938include DOL_DOCUMENT_ROOT.'/core/tpl/massactions_pre.tpl.php';
939
940if (!empty($catid)) {
941 print "<div id='ways'>";
942 $c = new Categorie($db);
943 $ways = $c->print_all_ways(' &gt; ', 'product/list.php');
944 print " &gt; ".$ways[0]."<br>\n";
945 print "</div><br>";
946}
947
948if ($search_all) {
949 $setupstring = '';
950 foreach ($fieldstosearchall as $key => $val) {
951 $fieldstosearchall[$key] = $langs->trans($val);
952 $setupstring .= $key."=".$val.";";
953 }
954 print '<!-- Search done like if PRODUCT_QUICKSEARCH_ON_FIELDS = '.$setupstring.' -->'."\n";
955 print '<div class="divsearchfieldfilter">'.$langs->trans("FilterOnInto", $search_all).implode(', ', $fieldstosearchall).'</div>'."\n";
956}
957
958// Filter on categories
959$moreforfilter = '';
960if (isModEnabled('category') && $user->hasRight('categorie', 'read')) {
961 $formcategory = new FormCategory($db);
962 $moreforfilter .= $formcategory->getFilterBox(Categorie::TYPE_PRODUCT, $searchCategoryProductList, 'minwidth300', $searchCategoryProductOperator ? $searchCategoryProductOperator : 0);
963}
964
965// Show/hide child variant products
966if (isModEnabled('variants')) {
967 $moreforfilter .= '<div class="divsearchfield">';
968 $moreforfilter .= '<input type="checkbox" id="search_show_childproducts" name="search_show_childproducts"'.($show_childproducts ? 'checked="checked"' : '').'>';
969 $moreforfilter .= ' <label for="search_show_childproducts">'.$langs->trans('ShowChildProducts').'</label>';
970 $moreforfilter .= '</div>';
971}
972
973$parameters = array();
974$reshook = $hookmanager->executeHooks('printFieldPreListTitle', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
975if (empty($reshook)) {
976 $moreforfilter .= $hookmanager->resPrint;
977} else {
978 $moreforfilter = $hookmanager->resPrint;
979}
980
981if (!empty($moreforfilter)) {
982 print '<div class="liste_titre liste_titre_bydiv centpercent">';
983 print $moreforfilter;
984 print '</div>';
985}
986
987$varpage = empty($contextpage) ? $_SERVER["PHP_SELF"] : $contextpage;
988$htmlofselectarray = $form->multiSelectArrayWithCheckbox('selectedfields', $arrayfields, $varpage, getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')); // This also change content of $arrayfields with user setup
989$selectedfields = ($mode != 'kanban' ? $htmlofselectarray : '');
990$selectedfields .= (count($arrayofmassactions) ? $form->showCheckAddButtons('checkforselect', 1) : '');
991
992print '<div class="div-table-responsive">';
993print '<table class="tagtable nobottomiftotal liste'.($moreforfilter ? " listwithfilterbefore" : "").'">'."\n";
994
995// Fields title search
996// --------------------------------------------------------------------
997print '<tr class="liste_titre_filter">';
998// Action column
999if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1000 print '<td class="liste_titre center maxwidthsearch">';
1001 $searchpicto = $form->showFilterButtons('left');
1002 print $searchpicto;
1003 print '</td>';
1004}
1005if (!empty($arrayfields['p.rowid']['checked'])) {
1006 print '<td class="liste_titre left">';
1007 print '<input class="flat" type="text" name="search_id" size="4" value="'.dol_escape_htmltag($search_id).'">';
1008 print '</td>';
1009}
1010if (!empty($arrayfields['p.ref']['checked'])) {
1011 print '<td class="liste_titre left">';
1012 print '<input class="flat" type="text" name="search_ref" size="8" value="'.dol_escape_htmltag($search_ref).'">';
1013 print '</td>';
1014}
1015if (!empty($arrayfields['pfp.ref_fourn']['checked'])) {
1016 print '<td class="liste_titre left">';
1017 print '<input class="flat" type="text" name="search_ref_supplier" size="8" value="'.dol_escape_htmltag($search_ref_supplier).'">';
1018 print '</td>';
1019}
1020// Thumbnail
1021if (!empty($arrayfields['thumbnail']['checked'])) {
1022 print '<td class="liste_titre center">';
1023 print '</td>';
1024}
1025if (!empty($arrayfields['p.label']['checked'])) {
1026 print '<td class="liste_titre left">';
1027 print '<input class="flat width100" type="text" name="search_label" value="'.dol_escape_htmltag($search_label).'">';
1028 print '</td>';
1029}
1030// Type
1031if (!empty($arrayfields['p.fk_product_type']['checked'])) {
1032 print '<td class="liste_titre center">';
1033 $array = array('-1' => '&nbsp;', '0' => $langs->trans('Product'), '1' => $langs->trans('Service'));
1034 print $form->selectarray('search_type', $array, $search_type);
1035 print '</td>';
1036}
1037// Description
1038if (!empty($arrayfields['p.description']['checked'])) {
1039 print '<td class="liste_titre left">';
1040 print '</td>';
1041}
1042// Barcode
1043if (!empty($arrayfields['p.barcode']['checked'])) {
1044 print '<td class="liste_titre">';
1045 print '<input class="flat" type="text" name="search_barcode" size="6" value="'.dol_escape_htmltag($search_barcode).'">';
1046 print '</td>';
1047}
1048// Duration
1049if (!empty($arrayfields['p.duration']['checked'])) {
1050 print '<td class="liste_titre">';
1051 print '</td>';
1052}
1053// Parent
1054if (!empty($arrayfields['pac.fk_product_parent']['checked'])) {
1055 print '<td class="liste_titre">';
1056 print '</td>';
1057}
1058// Finished
1059if (!empty($arrayfields['p.finished']['checked'])) {
1060 print '<td class="liste_titre">';
1061 print $formproduct->selectProductNature('search_finished', $search_finished);
1062 print '</td>';
1063}
1064// Weight
1065if (!empty($arrayfields['p.weight']['checked'])) {
1066 print '<td class="liste_titre">';
1067 print '</td>';
1068}
1069// Weight units
1070if (!empty($arrayfields['p.weight_units']['checked'])) {
1071 print '<td class="liste_titre">';
1072 print '</td>';
1073}
1074// Length
1075if (!empty($arrayfields['p.length']['checked'])) {
1076 print '<td class="liste_titre">';
1077 print '</td>';
1078}
1079// Length units
1080if (!empty($arrayfields['p.length_units']['checked'])) {
1081 print '<td class="liste_titre">';
1082 print '</td>';
1083}
1084// Width
1085if (!empty($arrayfields['p.width']['checked'])) {
1086 print '<td class="liste_titre">';
1087 print '</td>';
1088}
1089// Width units
1090if (!empty($arrayfields['p.width_units']['checked'])) {
1091 print '<td class="liste_titre">';
1092 print '</td>';
1093}
1094// Height
1095if (!empty($arrayfields['p.height']['checked'])) {
1096 print '<td class="liste_titre">';
1097 print '</td>';
1098}
1099// Height units
1100if (!empty($arrayfields['p.height_units']['checked'])) {
1101 print '<td class="liste_titre">';
1102 print '</td>';
1103}
1104// Surface
1105if (!empty($arrayfields['p.surface']['checked'])) {
1106 print '<td class="liste_titre">';
1107 print '</td>';
1108}
1109// Surface units
1110if (!empty($arrayfields['p.surface_units']['checked'])) {
1111 print '<td class="liste_titre">';
1112 print '</td>';
1113}
1114// Volume
1115if (!empty($arrayfields['p.volume']['checked'])) {
1116 print '<td class="liste_titre">';
1117 print '</td>';
1118}
1119// Volume units
1120if (!empty($arrayfields['p.volume_units']['checked'])) {
1121 print '<td class="liste_titre">';
1122 print '</td>';
1123}
1124
1125// Unit
1126if (!empty($arrayfields['cu.label']['checked'])) {
1127 print '<td class="liste_titre">';
1128 print $form->selectUnits($search_units, 'search_units', 1);
1129 print '</td>';
1130}
1131
1132// Default workstation
1133if (!empty($arrayfields['p.fk_default_workstation']['checked'])) {
1134 print '<td class="liste_titre">';
1135 print '<input class="flat width75" type="text" name="search_default_workstation" value="'.dol_escape_htmltag($search_default_workstation).'">';
1136 print '</td>';
1137}
1138
1139// Sell price
1140if (!empty($arrayfields['p.sellprice']['checked'])) {
1141 print '<td class="liste_titre right">';
1142 print '</td>';
1143}
1144
1145// Multiprice
1146if (getDolGlobalString('PRODUIT_MULTIPRICES')) {
1147 foreach ($arraypricelevel as $key => $value) {
1148 if (!empty($arrayfields['p.sellprice'.$key]['checked'])) {
1149 print '<td class="liste_titre right">';
1150 print '</td>';
1151 }
1152 }
1153}
1154
1155// Minimum buying Price
1156if (!empty($arrayfields['p.minbuyprice']['checked'])) {
1157 print '<td class="liste_titre">';
1158 print '&nbsp;';
1159 print '</td>';
1160}
1161// Number buying Price
1162if (!empty($arrayfields['p.numbuyprice']['checked'])) {
1163 print '<td class="liste_titre">';
1164 print '&nbsp;';
1165 print '</td>';
1166}
1167// VAT or Sell Tax Rate
1168if (!empty($arrayfields['p.tva_tx']['checked'])) {
1169 print '<td class="liste_titre right">';
1170 print '<input class="right flat maxwidth50" placeholder="%" type="text" name="search_vatrate" size="1" value="'.dol_escape_htmltag($search_vatrate).'">';
1171 print '</td>';
1172}
1173// WAP
1174if (!empty($arrayfields['p.pmp']['checked'])) {
1175 print '<td class="liste_titre">';
1176 print '&nbsp;';
1177 print '</td>';
1178}
1179// cost_price
1180if (!empty($arrayfields['p.cost_price']['checked'])) {
1181 print '<td class="liste_titre">';
1182 print '&nbsp;';
1183 print '</td>';
1184}
1185// Limit for alert
1186if (!empty($arrayfields['p.seuil_stock_alerte']['checked'])) {
1187 print '<td class="liste_titre">';
1188 print '&nbsp;';
1189 print '</td>';
1190}
1191// Desired stock
1192if (!empty($arrayfields['p.desiredstock']['checked'])) {
1193 print '<td class="liste_titre">';
1194 print '&nbsp;';
1195 print '</td>';
1196}
1197// Stock
1198if (!empty($arrayfields['p.stock']['checked'])) {
1199 print '<td class="liste_titre">&nbsp;</td>';
1200}
1201// Stock
1202if (!empty($arrayfields['stock_virtual']['checked'])) {
1203 print '<td class="liste_titre">&nbsp;</td>';
1204}
1205// To batch
1206if (!empty($arrayfields['p.tobatch']['checked'])) {
1207 print '<td class="liste_titre center">';
1208 $statutarray = array(
1209 '-1' => '',
1210 '0' => $langs->trans("ProductStatusNotOnBatchShort"),
1211 '1' => $langs->trans("ProductStatusOnBatchShort"),
1212 '2' => $langs->trans("ProductStatusOnSerialShort")
1213 );
1214 print $form->selectarray('search_tobatch', $statutarray, $search_tobatch);
1215 print '</td>';
1216}
1217// Country
1218if (!empty($arrayfields['p.fk_country']['checked'])) {
1219 print '<td class="liste_titre center">';
1220 print $form->select_country($search_country, 'search_country', '', 0);
1221 print '</td>';
1222}
1223// State
1224if (!empty($arrayfields['p.fk_state']['checked'])) {
1225 print '<td class="liste_titre center">';
1226 print $formcompany->select_state($search_state, $search_country);
1227 print '</td>';
1228}
1229// Accountancy code sell
1230if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell']['checked'])) {
1231 print '<td class="liste_titre"><input class="flat maxwidth75" type="text" name="search_accountancy_code_sell" value="'.dol_escape_htmltag($search_accountancy_code_sell).'"></td>';
1232}
1233if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell_intra']['checked'])) {
1234 print '<td class="liste_titre"><input class="flat maxwidth75" type="text" name="search_accountancy_code_sell_intra" value="'.dol_escape_htmltag($search_accountancy_code_sell_intra).'"></td>';
1235}
1236if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell_export']['checked'])) {
1237 print '<td class="liste_titre"><input class="flat maxwidth75" type="text" name="search_accountancy_code_sell_export" value="'.dol_escape_htmltag($search_accountancy_code_sell_export).'"></td>';
1238}
1239// Accountancy code buy
1240if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy']['checked'])) {
1241 print '<td class="liste_titre"><input class="flat maxwidth75" type="text" name="search_accountancy_code_buy" value="'.dol_escape_htmltag($search_accountancy_code_buy).'"></td>';
1242}
1243if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy_intra']['checked'])) {
1244 print '<td class="liste_titre"><input class="flat maxwidth75" type="text" name="search_accountancy_code_buy_intra" value="'.dol_escape_htmltag($search_accountancy_code_buy_intra).'"></td>';
1245}
1246if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy_export']['checked'])) {
1247 print '<td class="liste_titre"><input class="flat maxwidth75" type="text" name="search_accountancy_code_buy_export" value="'.dol_escape_htmltag($search_accountancy_code_buy_export).'"></td>';
1248}
1249// Extra fields
1250include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_input.tpl.php';
1251// Fields from hook
1252$parameters = array('arrayfields' => $arrayfields);
1253$reshook = $hookmanager->executeHooks('printFieldListOption', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1254print $hookmanager->resPrint;
1255// Date creation
1256if (!empty($arrayfields['p.datec']['checked'])) {
1257 print '<td class="liste_titre">';
1258 print '</td>';
1259}
1260// Date modification
1261if (!empty($arrayfields['p.tms']['checked'])) {
1262 print '<td class="liste_titre">';
1263 print '</td>';
1264}
1265if (!empty($arrayfields['p.import_key']['checked'])) {
1266 print '<td class="liste_titre center">';
1267 print '<input class="flat maxwidth75" type="text" name="search_import_key" value="'.dol_escape_htmltag($search_import_key).'">';
1268 print '</td>';
1269}
1270if (!empty($arrayfields['p.tosell']['checked'])) {
1271 print '<td class="liste_titre center parentonrightofpage">';
1272 print $form->selectarray('search_tosell', array('0' => $langs->trans('ProductStatusNotOnSellShort'), '1' => $langs->trans('ProductStatusOnSellShort')), $search_tosell, 1, 0, 0, '', 0, 0, 0, '', 'search_status width100 onrightofpage');
1273 print '</td>';
1274}
1275if (!empty($arrayfields['p.tobuy']['checked'])) {
1276 print '<td class="liste_titre center parentonrightofpage">';
1277 print $form->selectarray('search_tobuy', array('0' => $langs->trans('ProductStatusNotOnBuyShort'), '1' => $langs->trans('ProductStatusOnBuyShort')), $search_tobuy, 1, 0, 0, '', 0, 0, 0, '', 'search_status width100 onrightofpage');
1278 print '</td>';
1279}
1280// Action column
1281if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1282 print '<td class="liste_titre center maxwidthsearch">';
1283 $searchpicto = $form->showFilterButtons();
1284 print $searchpicto;
1285 print '</td>';
1286}
1287print '</tr>'."\n";
1288
1289$totalarray = array();
1290$totalarray['nbfield'] = 0;
1291
1292// Fields title label
1293// --------------------------------------------------------------------
1294print '<tr class="liste_titre">';
1295// Action column
1296if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1297 print_liste_field_titre($selectedfields, $_SERVER["PHP_SELF"], "", '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ');
1298 $totalarray['nbfield']++;
1299}
1300if (!empty($arrayfields['p.rowid']['checked'])) {
1301 print_liste_field_titre($arrayfields['p.rowid']['label'], $_SERVER["PHP_SELF"], "p.rowid", "", $param, "", $sortfield, $sortorder);
1302 $totalarray['nbfield']++;
1303}
1304if (!empty($arrayfields['p.ref']['checked'])) {
1305 print_liste_field_titre($arrayfields['p.ref']['label'], $_SERVER["PHP_SELF"], "p.ref", "", $param, "", $sortfield, $sortorder);
1306 $totalarray['nbfield']++;
1307}
1308if (!empty($arrayfields['pfp.ref_fourn']['checked'])) {
1309 print_liste_field_titre($arrayfields['pfp.ref_fourn']['label'], $_SERVER["PHP_SELF"], "pfp.ref_fourn", "", $param, "", $sortfield, $sortorder);
1310 $totalarray['nbfield']++;
1311}
1312if (!empty($arrayfields['thumbnail']['checked'])) {
1313 print_liste_field_titre($arrayfields['thumbnail']['label'], $_SERVER["PHP_SELF"], '', '', $param, '', $sortfield, $sortorder, 'center ');
1314 $totalarray['nbfield']++;
1315}
1316if (!empty($arrayfields['p.label']['checked'])) {
1317 print_liste_field_titre($arrayfields['p.label']['label'], $_SERVER["PHP_SELF"], "p.label", "", $param, "", $sortfield, $sortorder);
1318 $totalarray['nbfield']++;
1319}
1320if (!empty($arrayfields['p.fk_product_type']['checked'])) {
1321 // @phan-suppress-next-line PhanTypeInvalidDimOffset
1322 print_liste_field_titre($arrayfields['p.fk_product_type']['label'], $_SERVER["PHP_SELF"], "p.fk_product_type", "", $param, "", $sortfield, $sortorder, 'center ');
1323 $totalarray['nbfield']++;
1324}
1325if (!empty($arrayfields['p.description']['checked'])) {
1326 print_liste_field_titre($arrayfields['p.description']['label'], $_SERVER["PHP_SELF"], "p.description", "", $param, "", $sortfield, $sortorder);
1327 $totalarray['nbfield']++;
1328}
1329if (!empty($arrayfields['p.barcode']['checked'])) {
1330 print_liste_field_titre($arrayfields['p.barcode']['label'], $_SERVER["PHP_SELF"], "p.barcode", "", $param, "", $sortfield, $sortorder);
1331 $totalarray['nbfield']++;
1332}
1333if (!empty($arrayfields['p.duration']['checked'])) {
1334 print_liste_field_titre($arrayfields['p.duration']['label'], $_SERVER["PHP_SELF"], "p.duration", "", $param, '', $sortfield, $sortorder, 'center ');
1335 $totalarray['nbfield']++;
1336}
1337if (!empty($arrayfields['pac.fk_product_parent']['checked'])) {
1338 print_liste_field_titre($arrayfields['pac.fk_product_parent']['label'], $_SERVER["PHP_SELF"], "pac.fk_product_parent", "", $param, '', $sortfield, $sortorder, '', empty($arrayfields['pac.fk_product_parent']['help']) ? '' : $arrayfields['pac.fk_product_parent']['help']);
1339 $totalarray['nbfield']++;
1340}
1341if (!empty($arrayfields['p.finished']['checked'])) {
1342 print_liste_field_titre($arrayfields['p.finished']['label'], $_SERVER["PHP_SELF"], "p.finished", "", $param, '', $sortfield, $sortorder, 'center ');
1343 $totalarray['nbfield']++;
1344}
1345if (!empty($arrayfields['p.weight']['checked'])) {
1346 print_liste_field_titre($arrayfields['p.weight']['label'], $_SERVER['PHP_SELF'], 'p.weight', '', $param, '', $sortfield, $sortorder, 'center ');
1347 $totalarray['nbfield']++;
1348}
1349if (!empty($arrayfields['p.weight_units']['checked'])) {
1350 print_liste_field_titre($arrayfields['p.weight_units']['label'], $_SERVER['PHP_SELF'], 'p.weight_units', '', $param, '', $sortfield, $sortorder, 'center ');
1351 $totalarray['nbfield']++;
1352}
1353if (!empty($arrayfields['p.length']['checked'])) {
1354 print_liste_field_titre($arrayfields['p.length']['label'], $_SERVER['PHP_SELF'], 'p.length', '', $param, '', $sortfield, $sortorder, 'center ');
1355 $totalarray['nbfield']++;
1356}
1357if (!empty($arrayfields['p.length_units']['checked'])) {
1358 print_liste_field_titre($arrayfields['p.length_units']['label'], $_SERVER['PHP_SELF'], 'p.length_units', '', $param, '', $sortfield, $sortorder, 'center ');
1359 $totalarray['nbfield']++;
1360}
1361if (!empty($arrayfields['p.width']['checked'])) {
1362 print_liste_field_titre($arrayfields['p.width']['label'], $_SERVER['PHP_SELF'], 'p.width', '', $param, '', $sortfield, $sortorder, 'center ');
1363 $totalarray['nbfield']++;
1364}
1365if (!empty($arrayfields['p.width_units']['checked'])) {
1366 print_liste_field_titre($arrayfields['p.width_units']['label'], $_SERVER['PHP_SELF'], 'p.width_units', '', $param, '', $sortfield, $sortorder, 'center ');
1367 $totalarray['nbfield']++;
1368}
1369if (!empty($arrayfields['p.height']['checked'])) {
1370 print_liste_field_titre($arrayfields['p.height']['label'], $_SERVER['PHP_SELF'], 'p.height', '', $param, '', $sortfield, $sortorder, 'center ');
1371 $totalarray['nbfield']++;
1372}
1373if (!empty($arrayfields['p.height_units']['checked'])) {
1374 print_liste_field_titre($arrayfields['p.height_units']['label'], $_SERVER['PHP_SELF'], 'p.height_units', '', $param, '', $sortfield, $sortorder, 'center ');
1375 $totalarray['nbfield']++;
1376}
1377if (!empty($arrayfields['p.surface']['checked'])) {
1378 print_liste_field_titre($arrayfields['p.surface']['label'], $_SERVER['PHP_SELF'], "p.surface", '', $param, '', $sortfield, $sortorder, 'center ');
1379 $totalarray['nbfield']++;
1380}
1381if (!empty($arrayfields['p.surface_units']['checked'])) {
1382 print_liste_field_titre($arrayfields['p.surface_units']['label'], $_SERVER['PHP_SELF'], 'p.surface_units', '', $param, '', $sortfield, $sortorder, 'center ');
1383 $totalarray['nbfield']++;
1384}
1385if (!empty($arrayfields['p.volume']['checked'])) {
1386 print_liste_field_titre($arrayfields['p.volume']['label'], $_SERVER['PHP_SELF'], 'p.volume', '', $param, '', $sortfield, $sortorder, 'center ');
1387 $totalarray['nbfield']++;
1388}
1389if (!empty($arrayfields['p.volume_units']['checked'])) {
1390 print_liste_field_titre($arrayfields['p.volume_units']['label'], $_SERVER['PHP_SELF'], 'p.volume_units', '', $param, '', $sortfield, $sortorder, 'center ');
1391 $totalarray['nbfield']++;
1392}
1393if (!empty($arrayfields['cu.label']['checked'])) {
1394 print_liste_field_titre($arrayfields['cu.label']['label'], $_SERVER['PHP_SELF'], '', '', $param, '', $sortfield, $sortorder, 'center ');
1395 $totalarray['nbfield']++;
1396}
1397if (!empty($arrayfields['p.fk_default_workstation']['checked'])) {
1398 print_liste_field_titre($arrayfields['p.fk_default_workstation']['label'], $_SERVER['PHP_SELF'], 'ws.ref', '', $param, '', $sortfield, $sortorder);
1399 $totalarray['nbfield']++;
1400}
1401if (!empty($arrayfields['p.sellprice']['checked'])) {
1402 print_liste_field_titre($arrayfields['p.sellprice']['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ');
1403 $totalarray['nbfield']++;
1404}
1405
1406// Multiprices
1407if (getDolGlobalString('PRODUIT_MULTIPRICES')) {
1408 foreach ($arraypricelevel as $key => $value) {
1409 if (!empty($arrayfields['p.sellprice'.$key]['checked'])) {
1410 print_liste_field_titre($arrayfields['p.sellprice'.$key]['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ');
1411 $totalarray['nbfield']++;
1412 }
1413 }
1414}
1415
1416if (!empty($arrayfields['p.minbuyprice']['checked'])) {
1417 print_liste_field_titre($arrayfields['p.minbuyprice']['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ');
1418 $totalarray['nbfield']++;
1419}
1420if (!empty($arrayfields['p.numbuyprice']['checked'])) {
1421 print_liste_field_titre($arrayfields['p.numbuyprice']['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ');
1422 $totalarray['nbfield']++;
1423}
1424if (!empty($arrayfields['p.tva_tx']['checked'])) {
1425 print_liste_field_titre($arrayfields['p.tva_tx']['label'], $_SERVER["PHP_SELF"], 'p.tva_tx', "", $param, '', $sortfield, $sortorder, 'right ');
1426 $totalarray['nbfield']++;
1427}
1428if (!empty($arrayfields['p.pmp']['checked'])) {
1429 print_liste_field_titre($arrayfields['p.pmp']['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ');
1430 $totalarray['nbfield']++;
1431}
1432if (!empty($arrayfields['p.cost_price']['checked'])) {
1433 print_liste_field_titre($arrayfields['p.cost_price']['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ');
1434 $totalarray['nbfield']++;
1435}
1436if (!empty($arrayfields['p.seuil_stock_alerte']['checked'])) {
1437 print_liste_field_titre($arrayfields['p.seuil_stock_alerte']['label'], $_SERVER["PHP_SELF"], "p.seuil_stock_alerte", "", $param, '', $sortfield, $sortorder, 'right ');
1438 $totalarray['nbfield']++;
1439}
1440if (!empty($arrayfields['p.desiredstock']['checked'])) {
1441 print_liste_field_titre($arrayfields['p.desiredstock']['label'], $_SERVER["PHP_SELF"], "p.desiredstock", "", $param, '', $sortfield, $sortorder, 'right ');
1442 $totalarray['nbfield']++;
1443}
1444if (!empty($arrayfields['p.stock']['checked'])) {
1445 print_liste_field_titre($arrayfields['p.stock']['label'], $_SERVER["PHP_SELF"], "p.stock", "", $param, '', $sortfield, $sortorder, 'right ');
1446 $totalarray['nbfield']++;
1447}
1448if (!empty($arrayfields['stock_virtual']['checked'])) {
1449 print_liste_field_titre($arrayfields['stock_virtual']['label'], $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'right ', 'VirtualStockDesc');
1450 $totalarray['nbfield']++;
1451}
1452if (!empty($arrayfields['p.tobatch']['checked'])) {
1453 print_liste_field_titre($arrayfields['p.tobatch']['label'], $_SERVER["PHP_SELF"], "p.tobatch", "", $param, '', $sortfield, $sortorder, 'center ');
1454 $totalarray['nbfield']++;
1455}
1456if (!empty($arrayfields['p.fk_country']['checked'])) {
1457 print_liste_field_titre($arrayfields['p.fk_country']['label'], $_SERVER["PHP_SELF"], "p.fk_country", "", $param, '', $sortfield, $sortorder);
1458 $totalarray['nbfield']++;
1459}
1460if (!empty($arrayfields['p.fk_state']['checked'])) {
1461 print_liste_field_titre($arrayfields['p.fk_state']['label'], $_SERVER["PHP_SELF"], "p.fk_state", "", $param, '', $sortfield, $sortorder);
1462 $totalarray['nbfield']++;
1463}
1464if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell']['checked'])) {
1465 print_liste_field_titre($arrayfields[$alias_product_perentity . '.accountancy_code_sell']['label'], $_SERVER["PHP_SELF"], $alias_product_perentity . ".accountancy_code_sell", "", $param, '', $sortfield, $sortorder);
1466 $totalarray['nbfield']++;
1467}
1468if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell_intra']['checked'])) {
1469 print_liste_field_titre($arrayfields[$alias_product_perentity . '.accountancy_code_sell_intra']['label'], $_SERVER["PHP_SELF"], $alias_product_perentity . ".accountancy_code_sell_intra", "", $param, '', $sortfield, $sortorder);
1470 $totalarray['nbfield']++;
1471}
1472if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell_export']['checked'])) {
1473 print_liste_field_titre($arrayfields[$alias_product_perentity . '.accountancy_code_sell_export']['label'], $_SERVER["PHP_SELF"], $alias_product_perentity . ".accountancy_code_sell_export", "", $param, '', $sortfield, $sortorder);
1474 $totalarray['nbfield']++;
1475}
1476if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy']['checked'])) {
1477 print_liste_field_titre($arrayfields[$alias_product_perentity . '.accountancy_code_buy']['label'], $_SERVER["PHP_SELF"], $alias_product_perentity . ".accountancy_code_buy", "", $param, '', $sortfield, $sortorder);
1478 $totalarray['nbfield']++;
1479}
1480if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy_intra']['checked'])) {
1481 print_liste_field_titre($arrayfields[$alias_product_perentity . '.accountancy_code_buy_intra']['label'], $_SERVER["PHP_SELF"], $alias_product_perentity . ".accountancy_code_buy_intra", "", $param, '', $sortfield, $sortorder);
1482 $totalarray['nbfield']++;
1483}
1484if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy_export']['checked'])) {
1485 print_liste_field_titre($arrayfields[$alias_product_perentity . '.accountancy_code_buy_export']['label'], $_SERVER["PHP_SELF"], $alias_product_perentity . ".accountancy_code_buy_export", "", $param, '', $sortfield, $sortorder);
1486 $totalarray['nbfield']++;
1487}
1488// Extra fields
1489include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_title.tpl.php';
1490// Hook fields
1491$parameters = array('arrayfields' => $arrayfields, 'param' => $param, 'sortfield' => $sortfield, 'sortorder' => $sortorder, 'totalarray' => &$totalarray);
1492$reshook = $hookmanager->executeHooks('printFieldListTitle', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1493print $hookmanager->resPrint;
1494if (!empty($arrayfields['p.datec']['checked'])) {
1495 print_liste_field_titre($arrayfields['p.datec']['label'], $_SERVER["PHP_SELF"], "p.datec", "", $param, '', $sortfield, $sortorder, 'center nowrap ');
1496 $totalarray['nbfield']++;
1497}
1498if (!empty($arrayfields['p.tms']['checked'])) {
1499 print_liste_field_titre($arrayfields['p.tms']['label'], $_SERVER["PHP_SELF"], "p.tms", "", $param, '', $sortfield, $sortorder, 'center nowrap ');
1500 $totalarray['nbfield']++;
1501}
1502if (!empty($arrayfields['p.import_key']['checked'])) {
1503 print_liste_field_titre($arrayfields['p.import_key']['label'], $_SERVER["PHP_SELF"], "p.import_key", "", $param, '', $sortfield, $sortorder, 'center ');
1504 $totalarray['nbfield']++;
1505}
1506if (!empty($arrayfields['p.tosell']['checked'])) {
1507 print_liste_field_titre($arrayfields['p.tosell']['label'], $_SERVER["PHP_SELF"], "p.tosell", "", $param, '', $sortfield, $sortorder, 'center ');
1508 $totalarray['nbfield']++;
1509}
1510if (!empty($arrayfields['p.tobuy']['checked'])) {
1511 print_liste_field_titre($arrayfields['p.tobuy']['label'], $_SERVER["PHP_SELF"], "p.tobuy", "", $param, '', $sortfield, $sortorder, 'center ');
1512 $totalarray['nbfield']++;
1513}
1514// Action column
1515if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1516 print_liste_field_titre($selectedfields, $_SERVER["PHP_SELF"], "", '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ');
1517 $totalarray['nbfield']++;
1518}
1519print '</tr>'."\n";
1520
1521
1522// Loop on record
1523// --------------------------------------------------------------------
1524$i = 0;
1525$savnbfield = $totalarray['nbfield'];
1526$totalarray = array();
1527$totalarray['nbfield'] = 0;
1528$imaxinloop = ($limit ? min($num, $limit) : $num);
1529while ($i < $imaxinloop) {
1530 $obj = $db->fetch_object($resql);
1531 if (empty($obj)) {
1532 break; // Should not happen
1533 }
1534
1535 // Multilangs
1536 if (getDolGlobalInt('MAIN_MULTILANGS')) { // If multilang is enabled
1537 $sql = "SELECT label";
1538 $sql .= " FROM ".MAIN_DB_PREFIX."product_lang";
1539 $sql .= " WHERE fk_product = ".((int) $obj->rowid);
1540 $sql .= " AND lang = '".$db->escape($langs->getDefaultLang())."'";
1541 $sql .= " LIMIT 1";
1542
1543 $result = $db->query($sql);
1544 if ($result) {
1545 $objtp = $db->fetch_object($result);
1546 if (!empty($objtp->label)) {
1547 $obj->label = $objtp->label;
1548 }
1549 }
1550 }
1551
1552 $parameters = array('staticdata' => $obj);
1553 // Note that $action and $object may have been modified by hook
1554 // do product_static fetch in hook if wanted or anything else
1555 $reshook = $hookmanager->executeHooks('loadStaticObject', $parameters, $product_static, $action);
1556 if (empty($reshook)) {
1557 $product_static->id = $obj->rowid;
1558 $product_static->ref = $obj->ref;
1559 $product_static->description = $obj->description;
1560 $product_static->ref_fourn = empty($obj->ref_supplier) ? '' : $obj->ref_supplier; // deprecated
1561 $product_static->ref_supplier = empty($obj->ref_supplier) ? '' : $obj->ref_supplier;
1562 $product_static->label = $obj->label;
1563 $product_static->barcode = $obj->barcode;
1564 $product_static->finished = $obj->finished;
1565 $product_static->type = $obj->fk_product_type;
1566 $product_static->status_buy = $obj->tobuy;
1567 $product_static->status = $obj->tosell;
1568 $product_static->status_batch = $obj->tobatch;
1569 $product_static->entity = $obj->entity;
1570 $product_static->pmp = $obj->pmp;
1571 $product_static->accountancy_code_sell = $obj->accountancy_code_sell;
1572 $product_static->accountancy_code_sell_export = $obj->accountancy_code_sell_export;
1573 $product_static->accountancy_code_sell_intra = $obj->accountancy_code_sell_intra;
1574 $product_static->accountancy_code_buy = $obj->accountancy_code_buy;
1575 $product_static->accountancy_code_buy_intra = $obj->accountancy_code_buy_intra;
1576 $product_static->accountancy_code_buy_export = $obj->accountancy_code_buy_export;
1577 $product_static->length = $obj->length;
1578 $product_static->length_units = $obj->length_units;
1579 $product_static->width = $obj->width;
1580 $product_static->width_units = $obj->width_units;
1581 $product_static->height = $obj->height;
1582 $product_static->height_units = $obj->height_units;
1583 $product_static->weight = $obj->weight;
1584 $product_static->weight_units = $obj->weight_units;
1585 $product_static->volume = $obj->volume;
1586 $product_static->volume_units = $obj->volume_units;
1587 $product_static->surface = $obj->surface;
1588 $product_static->surface_units = $obj->surface_units;
1589 if (getDolGlobalString('PRODUCT_USE_UNITS')) {
1590 $product_static->fk_unit = $obj->fk_unit;
1591 }
1592 $product_static->import_key = $obj->import_key;
1593
1594 // STOCK_DISABLE_OPTIM_LOAD can be set to force load_stock whatever is permissions on stock.
1595 if ((isModEnabled('stock') && $user->hasRight('stock', 'lire') && $search_type != 1) || getDolGlobalString('STOCK_DISABLE_OPTIM_LOAD')) { // To optimize call of load_stock
1596 if ($product_static->type != 1 || getDolGlobalString('STOCK_SUPPORTS_SERVICES')) { // Not a service
1597 $option = 'nobatch';
1598 if (empty($arrayfields['stock_virtual']['checked'])) {
1599 $option .= ',novirtual';
1600 }
1601 $product_static->load_stock($option); // Load stock_reel + stock_warehouse. This can also call load_virtual_stock()
1602 }
1603 }
1604 }
1605
1606 $product_static->price = $obj->price;
1607
1608 $object = $product_static;
1609
1610 $usercancreadprice = getDolGlobalString('MAIN_USE_ADVANCED_PERMS') ? $user->hasRight('product', 'product_advance', 'read_prices') : $user->hasRight('product', 'lire');
1611 if ($product_static->isService()) {
1612 $usercancreadprice = getDolGlobalString('MAIN_USE_ADVANCED_PERMS') ? $user->hasRight('service', 'service_advance', 'read_prices') : $user->hasRight('service', 'lire');
1613 }
1614
1615 if ($mode == 'kanban') {
1616 if ($i == 0) {
1617 print '<tr class="trkanban"><td colspan="'.$savnbfield.'">';
1618 print '<div class="box-flex-container kanban">';
1619 }
1620
1621 // Output Kanban
1622 $selected = -1;
1623 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
1624 $selected = 0;
1625 if (in_array($object->id, $arrayofselected)) {
1626 $selected = 1;
1627 }
1628 }
1629 print $object->getKanbanView('', array('selected' => $selected));
1630 if ($i == ($imaxinloop - 1)) {
1631 print '</div>';
1632 print '</td></tr>';
1633 }
1634 } else {
1635 // Show line of result
1636 $j = 0;
1637 print '<tr data-rowid="'.$object->id.'" class="oddeven">';
1638
1639 // Action column
1640 if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1641 print '<td class="nowrap center">';
1642 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
1643 $selected = 0;
1644 if (in_array($object->id, $arrayofselected)) {
1645 $selected = 1;
1646 }
1647 print '<input id="cb'.$object->id.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$obj->rowid.'"'.($selected ? ' checked="checked"' : '').'>';
1648 }
1649 print '</td>';
1650 if (!$i) {
1651 $totalarray['nbfield']++;
1652 }
1653 }
1654 // Rowid
1655 if (!empty($arrayfields['p.rowid']['checked'])) {
1656 print '<td class="nowraponall">';
1657 print $product_static->id;
1658 print "</td>\n";
1659 if (!$i) {
1660 $totalarray['nbfield']++;
1661 }
1662 }
1663
1664 // Ref
1665 if (!empty($arrayfields['p.ref']['checked'])) {
1666 print '<td class="tdoverflowmax250">';
1667 print $product_static->getNomUrl(1);
1668 print "</td>\n";
1669 if (!$i) {
1670 $totalarray['nbfield']++;
1671 }
1672 }
1673
1674 // Ref supplier
1675 if (!empty($arrayfields['pfp.ref_fourn']['checked'])) {
1676 print '<td class="tdoverflowmax200">';
1677 print $product_static->getNomUrl(1);
1678 print "</td>\n";
1679 if (!$i) {
1680 $totalarray['nbfield']++;
1681 }
1682 }
1683
1684 // Thumbnail
1685 if (!empty($arrayfields['thumbnail']['checked'])) {
1686 $product_thumbnail_html = '';
1687 if (!empty($product_static->entity)) {
1688 $product_thumbnail = $product_static->show_photos('product', $conf->product->multidir_output[$product_static->entity], 1, 1, 0, 0, 0, 80);
1689 if ($product_static->nbphoto > 0) {
1690 $product_thumbnail_html = $product_thumbnail;
1691 }
1692 }
1693
1694 print '<td class="center">' . $product_thumbnail_html . '</td>';
1695 if (!$i) {
1696 $totalarray['nbfield']++;
1697 }
1698 }
1699
1700 // Label
1701 if (!empty($arrayfields['p.label']['checked'])) {
1702 print '<td class="tdoverflowmax200" title="'.dol_escape_htmltag($product_static->label).'">'.$product_static->label.'</td>';
1703 if (!$i) {
1704 $totalarray['nbfield']++;
1705 }
1706 }
1707
1708 // Type
1709 if (!empty($arrayfields['p.fk_product_type']['checked'])) {
1710 print '<td class="center">';
1711 $s = '';
1712 if ($product_static->type == 0) {
1713 $s .= img_picto($langs->trans("Product"), 'product', 'class="paddingleftonly paddingrightonly colorgrey"');
1714 } else {
1715 $s .= img_picto($langs->trans("Service"), 'service', 'class="paddingleftonly paddingrightonly colorgrey"');
1716 }
1717 print $s;
1718 print '</td>';
1719 if (!$i) {
1720 $totalarray['nbfield']++;
1721 }
1722 }
1723
1724 // Description
1725 if (!empty($arrayfields['p.description']['checked'])) {
1726 print '<td class="left">';
1727 // Since description can be very large (several pages of HTML-
1728 // code) we limit to the first two rows
1729 print dolGetFirstLineOfText($product_static->description, 2);
1730 print '</td>';
1731 if (!$i) {
1732 $totalarray['nbfield']++;
1733 }
1734 }
1735
1736 // Barcode
1737 if (!empty($arrayfields['p.barcode']['checked'])) {
1738 print '<td class="tdoverflowmax125" title="'.dol_escape_htmltag($product_static->barcode).'">'.dol_escape_htmltag($product_static->barcode).'</td>';
1739 if (!$i) {
1740 $totalarray['nbfield']++;
1741 }
1742 }
1743
1744 // Duration
1745 if (!empty($arrayfields['p.duration']['checked'])) {
1746 print '<td class="center nowraponall">';
1747
1748 if (preg_match('/([^a-z]+)[a-z]$/i', $obj->duration)) {
1749 $duration_value = substr($obj->duration, 0, dol_strlen($obj->duration) - 1);
1750 $duration_unit = substr($obj->duration, -1);
1751
1752 if ((float) $duration_value > 1) {
1753 $dur = array("i" => $langs->trans("Minutes"), "h" => $langs->trans("Hours"), "d" => $langs->trans("Days"), "w" => $langs->trans("Weeks"), "m" => $langs->trans("Months"), "y" => $langs->trans("Years"));
1754 } elseif ((float) $duration_value > 0) {
1755 $dur = array("i" => $langs->trans("Minute"), "h" => $langs->trans("Hour"), "d" => $langs->trans("Day"), "w" => $langs->trans("Week"), "m" => $langs->trans("Month"), "y" => $langs->trans("Year"));
1756 }
1757 print $duration_value;
1758 print((!empty($duration_unit) && isset($dur[$duration_unit]) && $duration_value != '') ? ' '.$langs->trans($dur[$duration_unit]) : '');
1759 } elseif (!preg_match('/^[a-z]$/i', $obj->duration)) { // If duration is a simple char (like 's' of 'm'), we do not show value
1760 print $obj->duration;
1761 }
1762
1763 print '</td>';
1764 if (!$i) {
1765 $totalarray['nbfield']++;
1766 }
1767 }
1768
1769 if (!empty($arrayfields['pac.fk_product_parent']['checked'])) {
1770 print '<td class="nowraponall">';
1771 if ($obj->fk_product_parent > 0) {
1772 if (!empty($conf->cache['product'][$obj->fk_product_parent])) {
1773 $product_parent_static = $conf->cache['product'][$obj->fk_product_parent];
1774 } else {
1775 $product_parent_static = new Product($db);
1776 $product_parent_static->fetch($obj->fk_product_parent);
1777 $conf->cache['product'][$obj->fk_product_parent] = $product_parent_static;
1778 }
1779 print $product_parent_static->getNomUrl(1);
1780 }
1781 print '</td>';
1782 if (!$i) {
1783 $totalarray['nbfield']++;
1784 }
1785 }
1786 // Finished
1787 if (!empty($arrayfields['p.finished']['checked'])) {
1788 print '<td class="center">';
1789 print $product_static->getLibFinished();
1790 print '</td>';
1791 if (!$i) {
1792 $totalarray['nbfield']++;
1793 }
1794 }
1795 // Weight
1796 if (!empty($arrayfields['p.weight']['checked'])) {
1797 print '<td class="center">';
1798 print $product_static->weight;
1799 print '</td>';
1800 if (!$i) {
1801 $totalarray['nbfield']++;
1802 }
1803 }
1804 // Weight units
1805 if (!empty($arrayfields['p.weight_units']['checked'])) {
1806 print '<td class="center">';
1807 if ($product_static->weight != '') {
1808 print measuringUnitString(0, 'weight', $product_static->weight_units);
1809 }
1810 print '</td>';
1811 if (!$i) {
1812 $totalarray['nbfield']++;
1813 }
1814 }
1815 // Length
1816 if (!empty($arrayfields['p.length']['checked'])) {
1817 print '<td class="center">';
1818 print $product_static->length;
1819 print '</td>';
1820 if (!$i) {
1821 $totalarray['nbfield']++;
1822 }
1823 }
1824 // Length units
1825 if (!empty($arrayfields['p.length_units']['checked'])) {
1826 print '<td class="center">';
1827 if ($product_static->length != '') {
1828 print measuringUnitString(0, 'size', $product_static->length_units);
1829 }
1830 print '</td>';
1831 if (!$i) {
1832 $totalarray['nbfield']++;
1833 }
1834 }
1835 // Width
1836 if (!empty($arrayfields['p.width']['checked'])) {
1837 print '<td align="center">';
1838 print $product_static->width;
1839 print '</td>';
1840 if (!$i) {
1841 $totalarray['nbfield']++;
1842 }
1843 }
1844 // Width units
1845 if (!empty($arrayfields['p.width_units']['checked'])) {
1846 print '<td class="center">';
1847 if ($product_static->width != '') {
1848 print measuringUnitString(0, 'size', $product_static->width_units);
1849 }
1850 print '</td>';
1851 if (!$i) {
1852 $totalarray['nbfield']++;
1853 }
1854 }
1855 // Height
1856 if (!empty($arrayfields['p.height']['checked'])) {
1857 print '<td align="center">';
1858 print $product_static->height;
1859 print '</td>';
1860 if (!$i) {
1861 $totalarray['nbfield']++;
1862 }
1863 }
1864 // Height units
1865 if (!empty($arrayfields['p.height_units']['checked'])) {
1866 print '<td class="center">';
1867 if ($product_static->height != '') {
1868 print measuringUnitString(0, 'size', $product_static->height_units);
1869 }
1870 print '</td>';
1871 if (!$i) {
1872 $totalarray['nbfield']++;
1873 }
1874 }
1875 // Surface
1876 if (!empty($arrayfields['p.surface']['checked'])) {
1877 print '<td class="center">';
1878 print $product_static->surface;
1879 print '</td>';
1880 if (!$i) {
1881 $totalarray['nbfield']++;
1882 }
1883 }
1884 // Surface units
1885 if (!empty($arrayfields['p.surface_units']['checked'])) {
1886 print '<td class="center">';
1887 if ($product_static->surface != '') {
1888 print measuringUnitString(0, 'surface', $product_static->surface_units);
1889 }
1890 print '</td>';
1891 if (!$i) {
1892 $totalarray['nbfield']++;
1893 }
1894 }
1895 // Volume
1896 if (!empty($arrayfields['p.volume']['checked'])) {
1897 print '<td class="center">';
1898 print $product_static->volume;
1899 print '</td>';
1900 if (!$i) {
1901 $totalarray['nbfield']++;
1902 }
1903 }
1904 // Volume units
1905 if (!empty($arrayfields['p.volume_units']['checked'])) {
1906 print '<td class="center">';
1907 if ($product_static->volume != '') {
1908 print measuringUnitString(0, 'volume', $product_static->volume_units);
1909 }
1910 print '</td>';
1911 if (!$i) {
1912 $totalarray['nbfield']++;
1913 }
1914 }
1915 // Unit
1916 if (!empty($arrayfields['cu.label']['checked'])) {
1917 print '<td align="center">';
1918 if (!empty($obj->cu_label)) {
1919 print $langs->trans($obj->cu_label);
1920 }
1921 print '</td>';
1922 if (!$i) {
1923 $totalarray['nbfield']++;
1924 }
1925 }
1926
1927 // Default Workstation
1928 if (!empty($arrayfields['p.fk_default_workstation']['checked'])) {
1929 print '<td align="left">';
1930 if (isModEnabled('workstation') && !empty($obj->fk_default_workstation)) {
1931 $workstation_static->id = $obj->fk_default_workstation;
1932 $workstation_static->ref = $obj->ref_workstation;
1933 $workstation_static->status = $obj->status_workstation;
1934
1935 print $workstation_static->getNomUrl(1);
1936 }
1937 print '</td>';
1938 if (!$i) {
1939 $totalarray['nbfield']++;
1940 }
1941 }
1942
1943 // Sell price
1944 if (!empty($arrayfields['p.sellprice']['checked'])) {
1945 print '<td class="right nowraponall">';
1946 if ($product_static->status && $usercancreadprice) {
1947 if ($obj->price_base_type == 'TTC') {
1948 print '<span class="amount">'.price($obj->price_ttc).' '.$langs->trans("TTC").'</span>';
1949 } else {
1950 print '<span class="amount">'.price($obj->price).' '.$langs->trans("HT").'</span>';
1951 }
1952 }
1953 print '</td>';
1954 if (!$i) {
1955 $totalarray['nbfield']++;
1956 }
1957 }
1958
1959 // Multiprices
1960 if (getDolGlobalString('PRODUIT_MULTIPRICES')) {
1961 if (! isset($productpricescache)) {
1962 $productpricescache = array();
1963 }
1964 if (! isset($productpricescache[$obj->rowid])) {
1965 $productpricescache[$obj->rowid] = array();
1966 }
1967
1968 if ($product_static->status && $usercancreadprice) {
1969 // Make 1 request for all price levels (without filter on price_level) and saved result into an cache array
1970 // then reuse the cache array if we need prices for other price levels
1971 $sqlp = "SELECT p.rowid, p.fk_product, p.price, p.price_ttc, p.price_level, p.date_price, p.price_base_type";
1972 $sqlp .= " FROM ".MAIN_DB_PREFIX."product_price as p";
1973 $sqlp .= " WHERE fk_product = ".((int) $obj->rowid);
1974 $sqlp .= " ORDER BY p.date_price DESC, p.rowid DESC, p.price_level ASC";
1975 $resultp = $db->query($sqlp);
1976 if ($resultp) {
1977 $nump = $db->num_rows($resultp);
1978 $j = 0;
1979 while ($j < $nump) {
1980 $objp = $db->fetch_object($resultp);
1981
1982 if (empty($productpricescache[$obj->rowid][$objp->price_level])) {
1983 $productpricescache[$obj->rowid][$objp->price_level]['price'] = $objp->price;
1984 $productpricescache[$obj->rowid][$objp->price_level]['price_ttc'] = $objp->price_ttc;
1985 $productpricescache[$obj->rowid][$objp->price_level]['price_base_type'] = $objp->price_base_type;
1986 }
1987
1988 $j++;
1989 }
1990
1991 $db->free($resultp);
1992 } else {
1993 dol_print_error($db);
1994 }
1995 }
1996
1997 foreach ($arraypricelevel as $key => $value) {
1998 if (!empty($arrayfields['p.sellprice'.$key]['checked'])) {
1999 print '<td class="right nowraponall">';
2000 if (!empty($productpricescache[$obj->rowid]) && isset($productpricescache[$obj->rowid][$key]['price_base_type'])) {
2001 if ($productpricescache[$obj->rowid][$key]['price_base_type'] == 'TTC') {
2002 print '<span class="amount">'.price($productpricescache[$obj->rowid][$key]['price_ttc']).' '.$langs->trans("TTC").'</span>';
2003 } else {
2004 print '<span class="amount">'.price($productpricescache[$obj->rowid][$key]['price']).' '.$langs->trans("HT").'</span>';
2005 }
2006 }
2007 print '</td>';
2008 if (!$i) {
2009 $totalarray['nbfield']++;
2010 }
2011 }
2012 }
2013 }
2014
2015 // Better buy price
2016 if (!empty($arrayfields['p.minbuyprice']['checked'])) {
2017 print '<td class="right nowraponall">';
2018 if ($product_static->status_buy && $obj->bestpurchaseprice != '' && $usercancreadprice) {
2019 if ($product_fourn->find_min_price_product_fournisseur($obj->rowid) > 0) {
2020 if ($product_fourn->product_fourn_price_id > 0) {
2021 if ((isModEnabled("fournisseur") && $user->hasRight('fournisseur', 'lire') && !getDolGlobalString('MAIN_USE_NEW_SUPPLIERMOD')) || (isModEnabled("supplier_order") && $user->hasRight('supplier_order', 'lire')) || (isModEnabled("supplier_invoice") && $user->hasRight('supplier_invoice', 'lire'))) {
2022 $htmltext = $product_fourn->display_price_product_fournisseur(1, 1, 0, 1);
2023 print '<span class="amount">'.$form->textwithpicto(price($product_fourn->fourn_unitprice * (1 - $product_fourn->fourn_remise_percent / 100) - $product_fourn->fourn_remise).' '.$langs->trans("HT"), $htmltext).'</span>';
2024 } else {
2025 print '<span class="amount">'.price($product_fourn->fourn_unitprice).' '.$langs->trans("HT").'</span>';
2026 }
2027 }
2028 }
2029 }
2030 print '</td>';
2031 if (!$i) {
2032 $totalarray['nbfield']++;
2033 }
2034 }
2035
2036 // Number of buy prices - Vendor prices
2037 if (!empty($arrayfields['p.numbuyprice']['checked'])) {
2038 print '<td class="right">';
2039 if ($product_static->status_buy && $usercancreadprice) {
2040 if (count($productFournList = $product_fourn->list_product_fournisseur_price($obj->rowid)) > 0) {
2041 $htmltext = $product_fourn->display_price_product_fournisseur(1, 1, 0, 1, $productFournList);
2042 print $form->textwithpicto(count($productFournList), $htmltext);
2043 }
2044 }
2045 print '</td>';
2046 if (!$i) {
2047 $totalarray['nbfield']++;
2048 }
2049 }
2050
2051 // VAT or Sell Tax Rate
2052 if (!empty($arrayfields['p.tva_tx']['checked'])) {
2053 print '<td class="right">';
2054 print vatrate($obj->tva_tx, true);
2055 print '</td>';
2056 if (!$i) {
2057 $totalarray['nbfield']++;
2058 }
2059 }
2060
2061 // WAP
2062 if (!empty($arrayfields['p.pmp']['checked'])) {
2063 print '<td class="nowrap right">';
2064 if ($usercancreadprice) {
2065 print '<span class="amount">'.price($product_static->pmp, 1, $langs)."</span>";
2066 }
2067 print '</td>';
2068 if (!$i) {
2069 $totalarray['nbfield']++;
2070 }
2071 }
2072 // Cost price
2073 if (!empty($arrayfields['p.cost_price']['checked'])) {
2074 print '<td class="nowrap right">';
2075 //print $obj->cost_price;
2076 if ($usercancreadprice) {
2077 print '<span class="amount">'.price($obj->cost_price).' '.$langs->trans("HT").'</span>';
2078 }
2079 print '</td>';
2080 if (!$i) {
2081 $totalarray['nbfield']++;
2082 }
2083 }
2084
2085 // Limit alert
2086 if (!empty($arrayfields['p.seuil_stock_alerte']['checked'])) {
2087 print '<td class="right">';
2088 if ($product_static->type != 1) {
2089 print $obj->seuil_stock_alerte;
2090 }
2091 print '</td>';
2092 if (!$i) {
2093 $totalarray['nbfield']++;
2094 }
2095 }
2096 // Desired stock
2097 if (!empty($arrayfields['p.desiredstock']['checked'])) {
2098 print '<td class="right">';
2099 if ($product_static->type != 1) {
2100 print $obj->desiredstock;
2101 }
2102 print '</td>';
2103 if (!$i) {
2104 $totalarray['nbfield']++;
2105 }
2106 }
2107 // Stock real
2108 if (!empty($arrayfields['p.stock']['checked'])) {
2109 print '<td class="right">';
2110 if ($product_static->type != 1) {
2111 if ($obj->seuil_stock_alerte != '' && $product_static->stock_reel < (float) $obj->seuil_stock_alerte) {
2112 print img_warning($langs->trans("StockLowerThanLimit", $obj->seuil_stock_alerte)).' ';
2113 }
2114 if ($usercancreadprice) {
2115 if ($product_static->stock_reel < 0) {
2116 print '<span class="warning">';
2117 }
2118 print price(price2num($product_static->stock_reel, 'MS'), 0, $langs, 1, 0);
2119 if ($product_static->stock_reel < 0) {
2120 print '</span>';
2121 }
2122 }
2123 }
2124 print '</td>';
2125 if (!$i) {
2126 $totalarray['nbfield']++;
2127 }
2128 }
2129 // Stock virtual
2130 if (!empty($arrayfields['stock_virtual']['checked'])) {
2131 print '<td class="right">';
2132 if ($product_static->type != 1) {
2133 if ($obj->seuil_stock_alerte != '' && $product_static->stock_theorique < (float) $obj->seuil_stock_alerte) {
2134 print img_warning($langs->trans("StockLowerThanLimit", $obj->seuil_stock_alerte)).' ';
2135 }
2136 if ($usercancreadprice) {
2137 if ($product_static->stock_theorique < 0) {
2138 print '<span class="warning">';
2139 }
2140 print price(price2num($product_static->stock_theorique, 'MS'), 0, $langs, 1, 0);
2141 if ($product_static->stock_theorique < 0) {
2142 print '</span>';
2143 }
2144 }
2145 }
2146 print '</td>';
2147 if (!$i) {
2148 $totalarray['nbfield']++;
2149 }
2150 }
2151 // Lot/Serial
2152 if (!empty($arrayfields['p.tobatch']['checked'])) {
2153 print '<td class="center">';
2154 print $product_static->getLibStatut(1, 2);
2155 print '</td>';
2156 if (!$i) {
2157 $totalarray['nbfield']++;
2158 }
2159 }
2160 // Country
2161 if (!empty($arrayfields['p.fk_country']['checked'])) {
2162 print '<td>'.getCountry($obj->fk_country, '', $db).'</td>';
2163 if (!$i) {
2164 $totalarray['nbfield']++;
2165 }
2166 }
2167 // State
2168 if (!empty($arrayfields['p.fk_state']['checked'])) {
2169 print '<td>';
2170 if (!empty($obj->fk_state)) {
2171 print getState($obj->fk_state, '0', $db);
2172 }
2173 print '</td>';
2174 if (!$i) {
2175 $totalarray['nbfield']++;
2176 }
2177 }
2178 // Accountancy code sell
2179 if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell']['checked'])) {
2180 print '<td>'.length_accountg($product_static->accountancy_code_sell).'</td>';
2181 if (!$i) {
2182 $totalarray['nbfield']++;
2183 }
2184 }
2185 if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell_intra']['checked'])) {
2186 print '<td>'.length_accountg($product_static->accountancy_code_sell_intra).'</td>';
2187 if (!$i) {
2188 $totalarray['nbfield']++;
2189 }
2190 }
2191 if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_sell_export']['checked'])) {
2192 print '<td>'.length_accountg($product_static->accountancy_code_sell_export).'</td>';
2193 if (!$i) {
2194 $totalarray['nbfield']++;
2195 }
2196 }
2197 // Accountancy code buy
2198 if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy']['checked'])) {
2199 print '<td>'.length_accountg($product_static->accountancy_code_buy).'</td>';
2200 if (!$i) {
2201 $totalarray['nbfield']++;
2202 }
2203 }
2204 if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy_intra']['checked'])) {
2205 print '<td>'.length_accountg($product_static->accountancy_code_buy_intra).'</td>';
2206 if (!$i) {
2207 $totalarray['nbfield']++;
2208 }
2209 }
2210 if (!empty($arrayfields[$alias_product_perentity . '.accountancy_code_buy_export']['checked'])) {
2211 print '<td>'.length_accountg($product_static->accountancy_code_buy_export).'</td>';
2212 if (!$i) {
2213 $totalarray['nbfield']++;
2214 }
2215 }
2216 // Extra fields
2217 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_print_fields.tpl.php';
2218 // Fields from hook
2219 $parameters = array('arrayfields' => $arrayfields, 'obj' => $obj, 'i' => $i, 'totalarray' => &$totalarray);
2220 $reshook = $hookmanager->executeHooks('printFieldListValue', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
2221 print $hookmanager->resPrint;
2222 // Date creation
2223 if (!empty($arrayfields['p.datec']['checked'])) {
2224 print '<td class="center nowraponall">';
2225 print dol_print_date($db->jdate($obj->date_creation), 'dayhour', 'tzuser');
2226 print '</td>';
2227 if (!$i) {
2228 $totalarray['nbfield']++;
2229 }
2230 }
2231 // Date modification
2232 if (!empty($arrayfields['p.tms']['checked'])) {
2233 print '<td class="center nowraponall">';
2234 print dol_print_date($db->jdate($obj->date_modification), 'dayhour', 'tzuser');
2235 print '</td>';
2236 if (!$i) {
2237 $totalarray['nbfield']++;
2238 }
2239 }
2240
2241 // Import ID
2242 if (!empty($arrayfields['p.import_key']['checked'])) {
2243 print '<td class="center nowrap">';
2244 print dol_escape_htmltag($product_static->import_key);
2245 print '</td>';
2246 if (!$i) {
2247 $totalarray['nbfield']++;
2248 }
2249 }
2250
2251 // Status (to sell)
2252 if (!empty($arrayfields['p.tosell']['checked'])) {
2253 print '<td class="center nowrap">';
2254 if (!empty($conf->use_javascript_ajax) && $user->hasRight("produit", "creer") && getDolGlobalString('MAIN_DIRECT_STATUS_UPDATE')) {
2255 print ajax_object_onoff($product_static, 'status', 'tosell', 'ProductStatusOnSell', 'ProductStatusNotOnSell');
2256 } else {
2257 print $product_static->LibStatut($product_static->status, 5, 0);
2258 }
2259 print '</td>';
2260 if (!$i) {
2261 $totalarray['nbfield']++;
2262 }
2263 }
2264 // Status (to buy)
2265 if (!empty($arrayfields['p.tobuy']['checked'])) {
2266 print '<td class="center nowrap">';
2267 if (!empty($conf->use_javascript_ajax) && $user->hasRight("produit", "creer") && getDolGlobalString('MAIN_DIRECT_STATUS_UPDATE')) {
2268 print ajax_object_onoff($product_static, 'status_buy', 'tobuy', 'ProductStatusOnBuy', 'ProductStatusNotOnBuy');
2269 } else {
2270 print $product_static->LibStatut($product_static->status_buy, 5, 1);
2271 }
2272 print '</td>';
2273 if (!$i) {
2274 $totalarray['nbfield']++;
2275 }
2276 }
2277
2278 // Action column
2279 if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
2280 print '<td class="nowrap center">';
2281 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
2282 $selected = 0;
2283 if (in_array($object->id, $arrayofselected)) {
2284 $selected = 1;
2285 }
2286 print '<input id="cb'.$object->id.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$obj->rowid.'"'.($selected ? ' checked="checked"' : '').'>';
2287 }
2288 print '</td>';
2289 if (!$i) {
2290 $totalarray['nbfield']++;
2291 }
2292 }
2293
2294 print '</tr>'."\n";
2295 }
2296
2297 $i++;
2298}
2299
2300// If no record found
2301if ($num == 0) {
2302 $colspan = 1;
2303 foreach ($arrayfields as $key => $val) {
2304 if (!empty($val['checked'])) {
2305 $colspan++;
2306 }
2307 }
2308 print '<tr><td colspan="'.$colspan.'"><span class="opacitymedium">'.$langs->trans("NoRecordFound").'</span></td></tr>';
2309}
2310
2311$db->free($resql);
2312
2313print '</table>'."\n";
2314print '</div>'."\n";
2315
2316print '</form>'."\n";
2317
2318// End of page
2319llxFooter();
2320$db->close();
$id
Definition account.php:48
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:66
clean_account($account)
Return accounting account without zero on the right.
ajax_object_onoff($object, $code, $field, $text_on, $text_off, $input=array(), $morecss='', $htmlname='', $forcenojs=0, $moreparam='')
On/off button to change a property status of an object This uses the ajax service objectonoff....
Definition ajax.lib.php:750
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
Definition wrapper.php:87
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader($head='', $title='', $help_url='', $target='', $disablejs=0, $disablehead=0, $arrayofjs='', $arrayofcss='', $morequerystring='', $morecssonbody='', $replacemainareaby='', $disablenofollow=0, $disablenoindex=0)
Empty header.
Definition wrapper.php:71
Class to manage canvas.
Class to manage categories.
Class to manage standard extra fields.
Class to manage forms for categories.
Class to build HTML component for third parties management Only common components are here.
Class to manage generation of HTML components Only common components must be here.
Class with static methods for building HTML components related to products Only components common to ...
Class to manage predefined suppliers products.
Class to manage products or services.
const TYPE_PRODUCT
Regular product.
const TYPE_SERVICE
Service.
Class for Workstation.
getState($id, $withcode='0', $dbtouse=null, $withregion=0, $outputlangs=null, $entconv=1)
Return state translated from an id.
isInEEC($object)
Return if a country of an object is inside the EEC (European Economic Community)
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.
dolExplodeIntoArray($string, $delimiter=';', $kv='=')
Split a string with 2 keys into key array.
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_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dolGetFirstLineOfText($text, $nboflines=1, $charset='UTF-8')
Return first line of text.
price2num($amount, $rounding='', $option=0)
Function that return a number with universal decimal format (decimal separator is '.
dolGetButtonTitle($label, $helpText='', $iconClass='fa fa-file', $url='', $id='', $status=1, $params=array())
Function dolGetButtonTitle : this kind of buttons are used in title in list.
natural_search($fields, $value, $mode=0, $nofirstand=0)
Generate natural SQL search string for a criteria (this criteria can be tested on one or several fiel...
dol_strlen($string, $stringencoding='UTF-8')
Make a strlen call.
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.
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
dol_sort_array(&$array, $index, $order='asc', $natsort=0, $case_sensitive=0, $keepindex=0)
Advanced sort array by the value of a given key, which produces ascending (default) or descending out...
print_liste_field_titre($name, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $tooltip="", $forcenowrapcolumntitle=0)
Show title line of an array.
dolGetButtonTitleSeparator($moreClass="")
Add space between dolGetButtonTitle.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
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...
global $conf
The following vars must be defined: $type2label $form $conf, $lang, The following vars may also be de...
Definition member.php:79
measuringUnitString($unitid, $measuring_style='', $unitscale='', $use_short_label=0, $outputlangs=null)
Return translation label of a unit key.
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.