dolibarr 23.0.4
card.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2003-2006 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2011 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005 Simon Tosser <simon@kornog-computing.com>
5 * Copyright (C) 2005-2014 Regis Houssin <regis.houssin@inodbox.com>
6 * Copyright (C) 2016 Francis Appels <francis.appels@yahoo.com>
7 * Copyright (C) 2021 Noé Cendrier <noe.cendrier@altairis.fr>
8 * Copyright (C) 2021-2025 Frédéric France <frederic.france@free.fr>
9 * Copyright (C) 2022-2025 Charlene Benke <charlene@patas-monkey.com>
10 * Copyright (C) 2023 Christian Foellmann <christian@foellmann.de>
11 * Copyright (C) 2024-2025 MDW <mdeweerd@users.noreply.github.com>
12 *
13 * This program is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License as published by
15 * the Free Software Foundation; either version 3 of the License, or
16 * (at your option) any later version.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
22 *
23 * You should have received a copy of the GNU General Public License
24 * along with this program. If not, see <https://www.gnu.org/licenses/>.
25 */
26
33// Load Dolibarr environment
34require '../../main.inc.php';
35require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
36require_once DOL_DOCUMENT_ROOT.'/product/stock/class/entrepot.class.php';
37require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
38require_once DOL_DOCUMENT_ROOT.'/core/lib/stock.lib.php';
39require_once DOL_DOCUMENT_ROOT.'/core/lib/product.lib.php';
40require_once DOL_DOCUMENT_ROOT.'/core/class/html.formcompany.class.php';
41require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
42require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
43require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php';
44if (isModEnabled('project')) {
45 require_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
46 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formprojet.class.php';
47}
48
58// Load translation files required by the page
59$langs->loadLangs(array('products', 'stocks', 'companies', 'categories'));
60
61$action = GETPOST('action', 'aZ09');
62$cancel = GETPOST('cancel', 'alpha');
63$confirm = GETPOST('confirm');
64$backtopage = GETPOST('backtopage', 'alpha');
65$backtopageforcancel = GETPOST('backtopageforcancel', 'alpha');
66
67$projectid = GETPOSTINT('projectid');
68
69$id = GETPOSTINT('id');
70$socid = GETPOSTINT('socid');
71$ref = GETPOST('ref', 'alpha');
72
73// Load variable for pagination
74$limit = GETPOSTINT('limit') ? GETPOSTINT('limit') : $conf->liste_limit;
75$sortfield = GETPOST('sortfield', 'aZ09comma');
76$sortorder = GETPOST('sortorder', 'aZ09comma');
77if (!$sortfield) {
78 $sortfield = "p.ref";
79}
80if (!$sortorder) {
81 $sortorder = "DESC";
82}
83
84// Initialize a technical object to manage hooks of page. Note that conf->hooks_modules contains an array of hook context
85$hookmanager->initHooks(array('warehousecard', 'stocklist', 'globalcard'));
86
87// Security check
88$result=restrictedArea($user, 'stock', $id, 'entrepot&stock');
89
90$object = new Entrepot($db);
91$extrafields = new ExtraFields($db);
92
93// fetch optionals attributes and labels
94$extrafields->fetch_name_optionals_label($object->table_element);
95
96// Load object
97if ($id > 0 || !empty($ref)) {
98 $ret = $object->fetch($id, $ref);
99 if ($ret <= 0) {
100 setEventMessages($object->error, $object->errors, 'errors');
101 $action = '';
102 }
103}
104
105$usercanread = $user->hasRight('stock', 'lire');
106$usercancreate = $user->hasRight('stock', 'creer');
107$usercandelete = $user->hasRight('stock', 'supprimer');
108$permissiontoeditextra = $usercancreate;
109if (GETPOST('attribute', 'aZ09') && isset($extrafields->attributes[$object->table_element]['perms'][GETPOST('attribute', 'aZ09')])) {
110 // For action 'update_extras', is there a specific permission set for the attribute to update
111 $permissiontoeditextra = dol_eval((string) $extrafields->attributes[$object->table_element]['perms'][GETPOST('attribute', 'aZ09')]);
112}
113
114
115/*
116 * Actions
117 */
118
119$error = 0;
120
121$parameters = array('context' => 'warehousecard', 'id' => $id, 'ref' => $ref);
122$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
123if ($reshook < 0) {
124 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
125}
126if (empty($reshook)) {
127 $backurlforlist = DOL_URL_ROOT.'/product/stock/list.php';
128
129 if (empty($backtopage) || ($cancel && empty($id))) {
130 if (empty($backtopage) || ($cancel && strpos($backtopage, '__ID__'))) {
131 if (empty($id) && (($action != 'add' && $action != 'create') || $cancel)) {
132 $backtopage = $backurlforlist;
133 } else {
134 $backtopage = DOL_URL_ROOT.'/product/stock/card.php?id='.((!empty($id) && $id > 0) ? $id : '__ID__');
135 }
136 }
137 }
138
139 if ($cancel) {
140 if (!empty($backtopageforcancel)) {
141 header("Location: ".$backtopageforcancel);
142 exit;
143 } elseif (!empty($backtopage)) {
144 header("Location: ".$backtopage);
145 exit;
146 }
147 $action = '';
148 }
149
150 // Ajout entrepot
151 if ($action == 'add' && $user->hasRight('stock', 'creer')) {
152 $object->ref = (string) GETPOST("ref", "alpha");
153 $object->fk_parent = GETPOSTINT("fk_parent");
154 $object->fk_project = GETPOSTINT('projectid');
155 $object->label = (string) GETPOST("libelle", "alpha");
156 $object->description = (string) GETPOST("desc", "alpha");
157 $object->statut = GETPOSTINT("statut");
158 $object->lieu = (string) GETPOST("lieu", "alpha");
159 $object->address = (string) GETPOST("address", "alpha");
160 $object->zip = (string) GETPOST("zipcode", "alpha");
161 $object->town = (string) GETPOST("town", "alpha");
162 $object->country_id = GETPOSTINT("country_id");
163 $object->phone = (string) GETPOST("phone", "alpha");
164 $object->fax = (string) GETPOST("fax", "alpha");
165
166 if (!empty($object->label)) {
167 // Fill array 'array_options' with data from add form
168 $ret = $extrafields->setOptionalsFromPost(null, $object);
169 if ($ret < 0) {
170 $error++;
171 $action = 'create';
172 }
173
174 if (!$error) {
175 $id = $object->create($user);
176 if ($id > 0) {
177 setEventMessages($langs->trans("RecordSaved"), null, 'mesgs');
178
179 $categories = GETPOST('categories', 'array:int');
180 $object->setCategories($categories);
181 if (!empty($backtopage)) {
182 $backtopage = str_replace("__ID__", (string) $id, $backtopage);
183 header("Location: ".$backtopage);
184 exit;
185 } else {
186 header("Location: card.php?id=".urlencode((string) ($id)));
187 exit;
188 }
189 } else {
190 $action = 'create';
191 setEventMessages($object->error, $object->errors, 'errors');
192 }
193 }
194 } else {
195 setEventMessages($langs->trans("ErrorWarehouseRefRequired"), null, 'errors');
196 $action = "create"; // Force retour sur page creation
197 }
198 }
199
200 // Delete warehouse
201 if ($action == 'confirm_delete' && $confirm == 'yes' && $user->hasRight('stock', 'supprimer')) {
202 $object->fetch(GETPOSTINT('id'));
203 $result = $object->delete($user);
204 if ($result > 0) {
205 setEventMessages($langs->trans("RecordDeleted"), null, 'mesgs');
206 header("Location: ".DOL_URL_ROOT.'/product/stock/list.php?restore_lastsearch_values=1');
207 exit;
208 } else {
209 setEventMessages($object->error, $object->errors, 'errors');
210 $action = '';
211 }
212 }
213
214 // Update warehouse
215 if ($action == 'update' && !$cancel && $user->hasRight('stock', 'creer')) {
216 if ($object->fetch($id)) {
217 $object->label = GETPOST("libelle");
218 $object->fk_parent = GETPOSTINT("fk_parent");
219 $object->fk_project = GETPOSTINT('projectid');
220 $object->description = GETPOST("desc", 'restricthtml');
221 $object->statut = GETPOSTINT("statut");
222 $object->lieu = GETPOST("lieu");
223 $object->address = GETPOST("address");
224 $object->zip = GETPOST("zipcode");
225 $object->town = GETPOST("town");
226 $object->country_id = GETPOSTINT("country_id");
227 $object->phone = GETPOST("phone");
228 $object->fax = GETPOST("fax");
229
230 // Fill array 'array_options' with data from add form
231 $ret = $extrafields->setOptionalsFromPost(null, $object, '@GETPOSTISSET');
232 if ($ret < 0) {
233 $error++;
234 }
235
236 if (!$error) {
237 $ret = $object->update($id, $user);
238 if ($ret < 0) {
239 $error++;
240 }
241 }
242
243 if ($error) {
244 $action = 'edit';
245 setEventMessages($object->error, $object->errors, 'errors');
246 } else {
247 $categories = GETPOST('categories', 'array:int');
248 $object->setCategories($categories);
249 $action = '';
250 }
251 } else {
252 $action = 'edit';
253 setEventMessages($object->error, $object->errors, 'errors');
254 }
255 } elseif ($action == 'update_extras' && $permissiontoeditextra) {
256 $object->oldcopy = dol_clone($object, 2); // @phan-suppress-current-line PhanTypeMismatchProperty
257
258 $attribute_name = GETPOST('attribute', 'aZ09');
259
260 // Fill array 'array_options' with data from update form
261 $ret = $extrafields->setOptionalsFromPost(null, $object, $attribute_name);
262 if ($ret < 0) {
263 $error++;
264 }
265
266 if (!$error) {
267 $result = $object->updateExtraField($attribute_name, 'PRODUCT_MODIFY');
268 if ($result < 0) {
269 setEventMessages($object->error, $object->errors, 'errors');
270 $error++;
271 }
272 }
273
274 if ($error) {
275 $action = 'edit_extras';
276 }
277 } elseif ($action == 'classin' && $usercancreate) {
278 // Link to a project
279 $object->setProject(GETPOSTINT('projectid'));
280 }
281
282 if ($cancel == $langs->trans("Cancel")) {
283 $action = '';
284 }
285
286 // Actions when printing a doc from card
287 include DOL_DOCUMENT_ROOT.'/core/actions_printing.inc.php';
288
289 // Actions to build doc
290 $upload_dir = $conf->stock->dir_output;
291 $permissiontoadd = $user->hasRight('stock', 'creer');
292 include DOL_DOCUMENT_ROOT.'/core/actions_builddoc.inc.php';
293}
294
295
296/*
297 * View
298 */
299
300$productstatic = new Product($db);
301$form = new Form($db);
302$formproduct = new FormProduct($db);
303$formcompany = new FormCompany($db);
304$formfile = new FormFile($db);
305$formproject = null;
306if (isModEnabled('project')) {
307 $formproject = new FormProjets($db);
308}
309
310$title = $langs->trans("WarehouseCard");
311if ($action == 'create') {
312 $title = $langs->trans("NewWarehouse");
313}
314
315$help_url = 'EN:Module_Stocks_En|FR:Module_Stock|ES:M&oacute;dulo_Stocks';
316llxHeader("", $title, $help_url, '', 0, 0, '', '', '', 'mod-product page-stock_card');
317
318
319if ($action == 'create') {
320 print load_fiche_titre($langs->trans("NewWarehouse"), '', 'stock');
321
322 dol_set_focus('input[name="libelle"]');
323
324 print '<form action="'.$_SERVER["PHP_SELF"].'" method="post">'."\n";
325 print '<input type="hidden" name="token" value="'.newToken().'">';
326 print '<input type="hidden" name="action" value="add">';
327 print '<input type="hidden" name="backtopage" value="'.$backtopage.'">';
328
329 print dol_get_fiche_head();
330
331 print '<table class="border centpercent">';
332
333 // Ref
334 print '<tr><td class="titlefieldcreate fieldrequired">'.$langs->trans("Ref").'</td><td><input class="width200" name="libelle" value=""></td></tr>';
335
336 print '<tr><td>'.$langs->trans("LocationSummary").'</td><td><input name="lieu" size="40" value="'.(!empty($object->lieu) ? $object->lieu : '').'"></td></tr>';
337
338 // Parent entrepot
339 print '<tr><td>'.$langs->trans("AddIn").'</td><td>';
340 print img_picto('', 'stock', 'class="pictofixedwidth"').$formproduct->selectWarehouses((GETPOSTISSET('fk_parent') ? GETPOSTINT('fk_parent') : 'ifone'), 'fk_parent', '', 1);
341 print '</td></tr>';
342
343 // Project
344 if (isModEnabled('project') && $formproject !== null) {
345 $langs->load('projects');
346 print '<tr><td>'.$langs->trans('Project').'</td><td colspan="2">';
347 print img_picto('', 'project', 'class="pictofixedwidth"').$formproject->select_projects(($socid > 0 ? $socid : -1), (string) $projectid, 'projectid', 0, 0, 1, 1, 0, 0, 0, '', 1, 0, 'maxwidth500');
348 print ' <a href="'.DOL_URL_ROOT.'/projet/card.php?socid='.$socid.'&action=create&status=1&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create&socid='.$socid).'"><span class="fa fa-plus-circle valignmiddle" title="'.$langs->trans("AddProject").'"></span></a>';
349 print '</td></tr>';
350 }
351
352 // Description
353 print '<tr><td class="tdtop">'.$langs->trans("Description").'</td><td>';
354 // Editeur wysiwyg
355 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
356 $doleditor = new DolEditor('desc', (!empty($object->description) ? $object->description : ''), '', 180, 'dolibarr_notes', 'In', false, true, isModEnabled('fckeditor'), ROWS_5, '90%');
357 $doleditor->Create();
358 print '</td></tr>';
359
360 print '<tr><td>'.$langs->trans('Address').'</td><td><textarea name="address" class="quatrevingtpercent" rows="3" wrap="soft">';
361 print(!empty($object->address) ? $object->address : '');
362 print '</textarea></td></tr>';
363
364 // Zip / Town
365 print '<tr><td>'.$langs->trans('Zip').'</td><td>';
366 print $formcompany->select_ziptown((!empty($object->zip) ? $object->zip : ''), 'zipcode', array('town', 'selectcountry_id', 'state_id'), 6);
367 print '</td></tr>';
368 print '<tr><td>'.$langs->trans('Town').'</td><td>';
369 print $formcompany->select_ziptown((!empty($object->town) ? $object->town : ''), 'town', array('zipcode', 'selectcountry_id', 'state_id'));
370 print '</td></tr>';
371
372 // Country
373 print '<tr><td>'.$langs->trans('Country').'</td><td>';
374 print img_picto('', 'globe-americas', 'class="pictofixedwidth"');
375 print $form->select_country((!empty($object->country_id) ? $object->country_id : $mysoc->country_code), 'country_id');
376 if ($user->admin) {
377 print info_admin($langs->trans("YouCanChangeValuesForThisListFromDictionarySetup"), 1);
378 }
379 print '</td></tr>';
380
381 // Phone / Fax
382 print '<tr><td class="titlefieldcreate">'.$form->editfieldkey('Phone', 'phone', '', $object, 0).'</td><td>';
383 print img_picto('', 'object_phoning', 'class="pictofixedwidth"');
384 print '<input name="phone" size="20" value="'.$object->phone.'"></td></tr>';
385 print '<tr><td class="titlefieldcreate">'.$form->editfieldkey('Fax', 'fax', '', $object, 0).'</td>';
386 print '<td>';
387 print img_picto('', 'object_phoning_fax', 'class="pictofixedwidth"');
388 print '<input name="fax" size="20" value="'.$object->fax.'"></td></tr>';
389
390 // Warehouse usage
391 if (getDolGlobalInt("MAIN_FEATURES_LEVEL")) {
392 // TODO
393 }
394
395 // Status
396 print '<tr><td>'.$langs->trans("Status").'</td><td>';
397 print '<select id="warehousestatus" name="statut" class="flat minwidth100">';
398 foreach ($object->labelStatus as $key => $value) {
399 if ($key == 1) {
400 print '<option value="'.$key.'" selected>'.$langs->trans($value).'</option>';
401 } else {
402 print '<option value="'.$key.'">'.$langs->trans($value).'</option>';
403 }
404 }
405 print '</select>';
406 print ajax_combobox('warehousestatus');
407 print '</td></tr>';
408
409 // Other attributes
410 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_add.tpl.php';
411
412 if (isModEnabled('category')) {
413 // Categories
414 print '<tr><td>'.$langs->trans("Categories").'</td><td colspan="3">';
415 print $form->selectCategories(Categorie::TYPE_WAREHOUSE, 'categories', $object);
416 print "</td></tr>";
417 }
418 print '</table>';
419
420 print dol_get_fiche_end();
421
422 print $form->buttonsSaveCancel("Create");
423
424 print '</form>';
425} else {
426 $id = GETPOSTINT("id");
427 if ($id > 0 || $ref) {
428 $object = new Entrepot($db);
429 $result = $object->fetch($id, $ref);
430 if ($result <= 0) {
431 print 'No record found';
432 exit;
433 }
434
435 // View mode
436 if ($action != 'edit' && $action != 're-edit') {
437 $head = stock_prepare_head($object);
438
439 print dol_get_fiche_head($head, 'card', $langs->trans("Warehouse"), -1, 'stock');
440
441 $formconfirm = '';
442
443 // Confirm delete warehouse
444 if ($action == 'delete') {
445 $formquestion = array(
446 array('type' => 'other', 'name' => 'info', 'label' => img_warning('').$langs->trans("WarningThisWIllAlsoDeleteStock"), 'morecss' => 'warning')
447 );
448 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"]."?id=".$object->id, $langs->trans("DeleteAWarehouse"), $langs->trans("ConfirmDeleteWarehouse", $object->label), "confirm_delete", $formquestion, 0, 2);
449 }
450
451 // Call Hook formConfirm
452 $parameters = array('context' => 'warehousecard', 'formConfirm' => $formconfirm);
453 $reshook = $hookmanager->executeHooks('formConfirm', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
454 if (empty($reshook)) {
455 $formconfirm .= $hookmanager->resPrint;
456 } elseif ($reshook > 0) {
457 $formconfirm = $hookmanager->resPrint;
458 }
459
460 // Print form confirm
461 print $formconfirm;
462
463 // Warehouse card
464 $linkback = '<a href="'.DOL_URL_ROOT.'/product/stock/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
465
466 $morehtmlref = '<div class="refidno">';
467 $morehtmlref .= $langs->trans("LocationSummary").' : '.$object->lieu;
468
469 // Project
470 if (isModEnabled('project') && $formproject !== null) {
471 $langs->load("projects");
472 $morehtmlref .= '<br>'.img_picto('', 'project', 'class="pictofixedwidth"').' '.$langs->trans('Project').' ';
473 if ($usercancreate) {
474 if ($action != 'classify') {
475 $morehtmlref .= '<a class="editfielda" href="'.dolBuildUrl($_SERVER['PHP_SELF'], ['action' => 'classify', 'id' => $object->id], true).'">'.img_edit($langs->transnoentitiesnoconv('SetProject')).'</a> : ';
476 }
477 if ($action == 'classify') {
478 $projectid = $object->fk_project;
479 $morehtmlref .= '<form method="post" action="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'">';
480 $morehtmlref .= '<input type="hidden" name="action" value="classin">';
481 $morehtmlref .= '<input type="hidden" name="token" value="'.newToken().'">';
482 $morehtmlref .= $formproject->select_projects(($socid > 0 ? $socid : -1), (string) $projectid, 'projectid', 0, 0, 1, 1, 0, 0, 0, '', 1, 0, 'maxwidth500');
483 $morehtmlref .= '<input type="submit" class="button valignmiddle" value="'.$langs->trans("Modify").'">';
484 $morehtmlref .= '</form>';
485 } else {
486 $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'].'?id='.$object->id, ($socid > 0 ? $socid : -1), (string) $object->fk_project, 'none', 0, 0, 0, 1, '', 'maxwidth300');
487 }
488 } else {
489 if (!empty($object->fk_project)) {
490 $proj = new Project($db);
491 $proj->fetch($object->fk_project);
492 $morehtmlref .= ' : '.$proj->getNomUrl(1);
493 if ($proj->title) {
494 $morehtmlref .= ' - '.$proj->title;
495 }
496 } else {
497 $morehtmlref .= '';
498 }
499 }
500 }
501 $morehtmlref .= '</div>';
502
503 $shownav = 1;
504 if ($user->socid && !in_array('stock', explode(',', getDolGlobalString('MAIN_MODULES_FOR_EXTERNAL')))) {
505 $shownav = 0;
506 }
507
508 dol_banner_tab($object, 'ref', $linkback, $shownav, 'ref', 'ref', $morehtmlref);
509
510 print '<div class="fichecenter">';
511 print '<div class="fichehalfleft">';
512 print '<div class="underbanner clearboth"></div>';
513
514 print '<table class="border centpercent tableforfield">';
515
516 // Parent entrepot
517 $parentwarehouse = new Entrepot($db);
518 if (!empty($object->fk_parent) && $parentwarehouse->fetch($object->fk_parent) > 0) {
519 print '<tr><td>'.$langs->trans("ParentWarehouse").'</td><td>';
520 print $parentwarehouse->getNomUrl(3);
521 print '</td></tr>';
522 }
523
524 print '<tr>';
525
526 // Description
527 print '<td class="titlefield tdtop">'.$langs->trans("Description").'</td><td>'.dol_htmlentitiesbr($object->description).'</td></tr>';
528
529 // Warehouse usage
530 if (getDolGlobalInt("STOCK_USE_WAREHOUSE_USAGE")) {
531 $labelusagestring = $object->fields['warehouse_usage']['arrayofkeyval'][empty($object->warehouse_usage) ? 1 : $object->warehouse_usage];
532 $labelusage = $labelusagestring ? $langs->trans($labelusagestring) : 'Unknown';
533 print '<td class="titlefield tdtop">'.$langs->trans("WarehouseUsage").'</td><td>'.dol_htmlentitiesbr($labelusage).'</td></tr>';
534 }
535
536 $calcproductsunique = $object->nb_different_products();
537 $calcproducts = $object->nb_products();
538
539 // Total nb of different products
540 print '<tr><td>'.$langs->trans("NumberOfDifferentProducts").'</td><td>';
541 print empty($calcproductsunique['nb']) ? '0' : $calcproductsunique['nb'];
542 print "</td></tr>";
543
544 // Nb of products
545 print '<tr><td>'.$langs->trans("NumberOfProducts").'</td><td>';
546 $valtoshow = price2num($calcproducts['nb'], 'MS');
547 print empty($valtoshow) ? '0' : $valtoshow;
548 print "</td></tr>";
549
550 print '</table>';
551
552 print '</div>';
553 print '<div class="fichehalfright">';
554 print '<div class="underbanner clearboth"></div>';
555
556 print '<table class="border centpercent tableforfield">';
557
558 // Value
559 print '<tr><td class="titlefield">'.$langs->trans("EstimatedStockValueShort").'</td><td>';
560 print price((empty($calcproducts['value']) ? '0' : price2num($calcproducts['value'], 'MT')), 0, $langs, 0, -1, -1, $conf->currency);
561 print "</td></tr>";
562
563 // Last movement
564 if ($user->hasRight('stock', 'mouvement', 'lire')) {
565 $sql = "SELECT max(m.datem) as datem";
566 $sql .= " FROM ".MAIN_DB_PREFIX."stock_mouvement as m";
567 $sql .= " WHERE m.fk_entrepot = ".((int) $object->id);
568 $lastmovementdate = 0;
569 $resqlbis = $db->query($sql);
570 if ($resqlbis) {
571 $obj = $db->fetch_object($resqlbis);
572 $lastmovementdate = $db->jdate($obj->datem);
573 } else {
574 dol_print_error($db);
575 }
576 print '<tr><td>'.$langs->trans("LastMovement").'</td><td>';
577 if ($lastmovementdate) {
578 print dol_print_date($lastmovementdate, 'dayhour');
579 print ' &nbsp; &nbsp; ';
580 print img_picto($langs->trans('LastMovement'), 'movement', 'class="pictofixedwidth"');
581 print '<a href="'.DOL_URL_ROOT.'/product/stock/movement_list.php?id='.$object->id.'">'.$langs->trans("FullList").'</a>';
582 } else {
583 print $langs->trans("None");
584 }
585 print "</td></tr>";
586 }
587
588 // Other attributes
589 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
590
591 // Categories
592 if (isModEnabled('category')) {
593 print '<tr><td valign="middle">'.$langs->trans("Categories").'</td><td colspan="3">';
594 print $form->showCategories($object->id, Categorie::TYPE_WAREHOUSE, 1);
595 print "</td></tr>";
596 }
597
598 print "</table>";
599
600 print '</div>';
601 print '</div>';
602
603 print '<div class="clearboth"></div>';
604
605 print dol_get_fiche_end();
606
607
608 /*
609 * Action bar
610 */
611 print "<div class=\"tabsAction\">\n";
612
613 $parameters = array('context' => 'warehousecard');
614 $reshook = $hookmanager->executeHooks('addMoreActionsButtons', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
615 if (empty($reshook)) {
616 if (empty($action) || $action == 'classin') {
617 if ($user->hasRight('stock', 'creer')) {
618 print '<a class="butAction" href="card.php?action=edit&token='.newToken().'&id='.$object->id.'">'.$langs->trans("Modify").'</a>';
619 } else {
620 print '<a class="butActionRefused classfortooltip" href="#">'.$langs->trans("Modify").'</a>';
621 }
622
623 if ($user->hasRight('stock', 'supprimer')) {
624 print '<a class="butActionDelete" href="card.php?action=delete&token='.newToken().'&id='.$object->id.'">'.$langs->trans("Delete").'</a>';
625 } else {
626 print '<a class="butActionRefused classfortooltip" href="#">'.$langs->trans("Delete").'</a>';
627 }
628 }
629 }
630
631 print "</div>";
632
633 // Show list of products into warehouse
634
635 $totalarray = array();
636 $totalarray['val'] = array();
637 $totalarray['pos'] = array();
638 $totalarray['type'] = array();
639 $totalarray['nbfield'] = 0;
640
641 // TODO Create $arrayfields with all fields to show
642
643 print load_fiche_titre($langs->trans("Stock"), '', 'stock');
644
645 print '<div class="div-table-responsive">';
646 print '<table class="noborder centpercent liste">';
647 print '<tr class="liste_titre">';
648 $parameters = array('context' => 'warehousecard', 'totalarray' => &$totalarray);
649 $reshook = $hookmanager->executeHooks('printFieldPreListTitle', $parameters); // Note that $action and $object may have been modified by hook
650 print $hookmanager->resPrint;
651
652 print_liste_field_titre("Products", "", "p.ref", "", "&id=".$object->id, "", $sortfield, $sortorder);
653 print_liste_field_titre("Label", "", "p.label", "", "&id=".$object->id, "", $sortfield, $sortorder);
654 print_liste_field_titre("NumberOfUnit", "", "ps.reel", "", "&id=".$object->id, '', $sortfield, $sortorder, 'right ');
655 $totalarray['nbfield'] += 3;
656 $totalarray['pos'][$totalarray['nbfield']] = 'totalunit';
657 $totalarray['type'][$totalarray['nbfield']] = 'stock';
658
659 if (getDolGlobalString('PRODUCT_USE_UNITS')) {
660 print_liste_field_titre("Unit", "", "p.fk_unit", "", "&id=".$object->id, 'align="left"', $sortfield, $sortorder);
661 $totalarray['nbfield']++;
662 $totalarray['pos'][$totalarray['nbfield']] = 'units';
663 $totalarray['type'][$totalarray['nbfield']] = 'string';
664 }
665 $usercancreadsupplierprice = getDolGlobalString('MAIN_USE_ADVANCED_PERMS') ? $user->hasRight('product', 'product_advance', 'read_supplier_prices') : $user->hasRight('product', 'read');
666 if ($usercancreadsupplierprice) {
667 print_liste_field_titre($form->textwithpicto($langs->trans("AverageUnitPricePMPShort"), $langs->trans("AverageUnitPricePMPDesc")), "", "p.pmp", "", "&id=".$object->id, '', $sortfield, $sortorder, 'right ');
668 $totalarray['nbfield']++;
669
670 print_liste_field_titre("EstimatedStockValueShort", "", "svalue", "", "&id=".$object->id, '', $sortfield, $sortorder, 'right ');
671 $totalarray['nbfield']++;
672 $totalarray['pos'][$totalarray['nbfield']] = 'totalvalue';
673 $totalarray['type'][$totalarray['nbfield']] = '';
674 }
675
676 if (!getDolGlobalString('PRODUIT_MULTIPRICES') && !getDolGlobalString('PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES')) {
677 print_liste_field_titre("SellPriceMin", "", "p.price", "", "&id=".$object->id, '', $sortfield, $sortorder, 'right ');
678 $totalarray['nbfield']++;
679 }
680 if (!getDolGlobalString('PRODUIT_MULTIPRICES') && !getDolGlobalString('PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES')) {
681 print_liste_field_titre("EstimatedStockValueSellShort", "", "", "", "&id=".$object->id, '', $sortfield, $sortorder, 'right ');
682 $totalarray['nbfield']++;
683 $totalarray['pos'][$totalarray['nbfield']] = 'totalvaluesell';
684 $totalarray['type'][$totalarray['nbfield']] = '';
685 }
686 if ($user->hasRight('stock', 'mouvement', 'creer')) {
688 $totalarray['nbfield']++;
689 }
690 if ($user->hasRight('stock', 'creer')) {
692 $totalarray['nbfield']++;
693 }
694 // Hook fields
695 $parameters = array('context' => 'warehousecard', 'sortfield' => $sortfield, 'sortorder' => $sortorder, 'totalarray' => &$totalarray);
696 $reshook = $hookmanager->executeHooks('printFieldListTitle', $parameters); // Note that $action and $object may have been modified by hook
697 print $hookmanager->resPrint;
698 print "</tr>\n";
699
700 $totalunit = 0;
701 $totalvalue = $totalvaluesell = 0;
702
703 //For MultiCompany PMP per entity
704 $separatedPMP = false;
705 if (getDolGlobalString('MULTICOMPANY_PRODUCT_SHARING_ENABLED') && getDolGlobalString('MULTICOMPANY_PMP_PER_ENTITY_ENABLED')) {
706 $separatedPMP = true;
707 }
708
709 $sql = "SELECT p.rowid as rowid, p.ref, p.label as produit, p.tobatch, p.fk_product_type as type, p.price, p.price_ttc, p.entity,";
710 $sql .= "p.tosell, p.tobuy,";
711 $sql .= "p.accountancy_code_sell,";
712 $sql .= "p.accountancy_code_sell_intra,";
713 $sql .= "p.accountancy_code_sell_export,";
714 $sql .= "p.accountancy_code_buy,";
715 $sql .= "p.accountancy_code_buy_intra,";
716 $sql .= "p.accountancy_code_buy_export,";
717 $sql .= 'p.barcode,';
718 if ($separatedPMP) {
719 // COALESCE: a product may have no row yet in llx_product_perentity (rows are created
720 // on the first stock movement), so fall back on the global p.pmp like Product::fetch()
721 // does, instead of showing an empty AWP.
722 $sql .= " COALESCE(pa.pmp, p.pmp) as ppmp,";
723 } else {
724 $sql .= " p.pmp as ppmp,";
725 }
726 $sql .= " ps.reel as value";
727 if (getDolGlobalString('PRODUCT_USE_UNITS')) {
728 $sql .= ",fk_unit";
729 }
730 // svalue is the sort key of the "estimated value" column, so it must use the same AWP
731 // as ppmp above (the displayed value is recomputed in PHP from ppmp).
732 if ($separatedPMP) {
733 $sql .= ", (ps.reel * COALESCE(pa.pmp, p.pmp)) as svalue";
734 } else {
735 $sql .= ", (ps.reel * p.pmp) as svalue";
736 }
737 // Add fields from hooks
738 $parameters = array('context' => 'warehousecard');
739 $reshook = $hookmanager->executeHooks('printFieldListSelect', $parameters); // Note that $action and $object may have been modified by hook
740 if ($reshook > 0) { //Note that $sql is replaced if reshook > 0
741 $sql = "";
742 }
743 $sql .= $hookmanager->resPrint;
744 $sql .= " FROM ".MAIN_DB_PREFIX."product_stock as ps, ".MAIN_DB_PREFIX."product as p";
745
746 if ($separatedPMP) {
747 // LEFT JOIN (not an inner join): a product with no llx_product_perentity row must
748 // still be listed in the warehouse content, falling back on the global p.pmp.
749 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product_perentity as pa ON pa.fk_product = p.rowid AND pa.entity = ".((int) $conf->entity);
750 }
751 $parameters = array('context' => 'warehousecard');
752 $reshook = $hookmanager->executeHooks('printFieldListFrom', $parameters); // Note that $action and $object may have been modified by hook
753 if ($reshook > 0) { //Note that $sql is replaced if reshook > 0
754 $sql = "";
755 }
756 $sql .= $hookmanager->resPrint;
757
758 $sql .= " WHERE ps.fk_product = p.rowid";
759 $sql .= " AND ps.reel <> 0"; // We do not show if stock is 0 (no product in this warehouse)
760 $sql .= " AND ps.fk_entrepot = ".((int) $object->id);
761
762 $parameters = array('context' => 'warehousecard');
763 $reshook = $hookmanager->executeHooks('printFieldListWhere', $parameters); // Note that $action and $object may have been modified by hook
764 if ($reshook > 0) { //Note that $sql is replaced if reshook > 0
765 $sql = "";
766 }
767 $sql .= $hookmanager->resPrint;
768
769 $sql .= $db->order($sortfield, $sortorder);
770
771 dol_syslog('List products', LOG_DEBUG);
772 $resql = $db->query($sql);
773 if ($resql) {
774 $num = $db->num_rows($resql);
775 $i = 0;
776 $units = 0;
777 $sameunits = true;
778
779 while ($i < $num) {
780 $objp = $db->fetch_object($resql);
781
782 // Multilangs
783 if (getDolGlobalInt('MAIN_MULTILANGS')) { // si l'option est active
784 $sql = "SELECT label";
785 $sql .= " FROM ".MAIN_DB_PREFIX."product_lang";
786 $sql .= " WHERE fk_product = ".((int) $objp->rowid);
787 $sql .= " AND lang = '".$db->escape($langs->getDefaultLang())."'";
788 $sql .= " LIMIT 1";
789
790 $result = $db->query($sql);
791 if ($result) {
792 $objtp = $db->fetch_object($result);
793 if (isset($objtp->label) && $objtp->label != '') {
794 $objp->produit = $objtp->label;
795 }
796 }
797 }
798
799 //print '<td>'.dol_print_date($objp->datem).'</td>';
800 print '<tr class="oddeven">';
801
802 $productstatic->id = $objp->rowid;
803 $productstatic->ref = $objp->ref;
804 $productstatic->label = $objp->produit;
805 $productstatic->type = $objp->type;
806 $productstatic->entity = $objp->entity;
807 $productstatic->status_batch = $objp->tobatch;
808 if (getDolGlobalString('PRODUCT_USE_UNITS')) {
809 $productstatic->fk_unit = $objp->fk_unit;
810 }
811 $productstatic->status = $objp->tosell;
812 $productstatic->status_buy = $objp->tobuy;
813 $productstatic->barcode = $objp->barcode;
814 $productstatic->accountancy_code_sell = $objp->accountancy_code_sell;
815 $productstatic->accountancy_code_sell_intra = $objp->accountancy_code_sell_intra;
816 $productstatic->accountancy_code_sell_export = $objp->accountancy_code_sell_export;
817 $productstatic->accountancy_code_buy = $objp->accountancy_code_buy;
818 $productstatic->accountancy_code_buy_intra = $objp->accountancy_code_buy_intra;
819 $productstatic->accountancy_code_buy_export = $objp->accountancy_code_buy_export;
820
821 // Ref
822 print "<td>";
823 print $productstatic->getNomUrl(1, 'stock', 16);
824 print '</td>';
825
826 // Label
827 print '<td class="tdoverflowmax200" title="'.dol_escape_htmltag($objp->produit).'">'.dol_escape_htmltag($objp->produit).'</td>';
828
829 // Value
830 print '<td class="right">';
831 $valtoshow = price(price2num($objp->value, 'MS'), 0, '', 0, 0); // TODO replace with a qty() function
832 print empty($valtoshow) ? '0' : $valtoshow;
833 print '</td>';
834 $totalunit += $objp->value;
835
836 if (getDolGlobalString('PRODUCT_USE_UNITS')) {
837 // Units
838 print '<td align="left">';
839 if (is_null($productstatic->fk_unit)) {
840 $productstatic->fk_unit = 1;
841 }
842 print $productstatic->getLabelOfUnit('long', $langs);
843 print '</td>';
844 }
845 if ($usercancreadsupplierprice) {
846 // Price buy PMP
847 print '<td class="right nowraponall">'.price(price2num($objp->ppmp, 'MU')).'</td>';
848
849 // Total PMP
850 print '<td class="right amount nowraponall">'.price(price2num($objp->ppmp * $objp->value, 'MT')).'</td>';
851 $totalvalue += price2num($objp->ppmp * $objp->value, 'MT');
852 }
853 $pricemin = 0;
854 // Price sell min
855 if (!getDolGlobalString('PRODUIT_MULTIPRICES') && !getDolGlobalString('PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES')) {
856 $pricemin = $objp->price;
857 print '<td class="right">';
858 print price(price2num($pricemin, 'MU'), 1);
859 print '</td>';
860 // Total sell min
861 print '<td class="right">';
862 print price(price2num($pricemin * $objp->value, 'MT'), 1);
863 print '</td>';
864 }
865 $totalvaluesell += price2num($pricemin * $objp->value, 'MT');
866
867 // Link to transfer
868 if ($user->hasRight('stock', 'mouvement', 'creer')) {
869 print '<td class="center"><a href="'.DOL_URL_ROOT.'/product/stock/product.php?dwid='.$object->id.'&id='.$objp->rowid.'&action=transfer&token='.newToken().'&backtopage='.urlencode($_SERVER["PHP_SELF"].'?id='.$id).'">';
870 print img_picto($langs->trans("TransferStock"), 'add', 'class="hideonsmartphone pictofixedwidth" style="color: #a69944"');
871 print $langs->trans("TransferStock");
872 print "</a></td>";
873 }
874
875 // Link to stock
876 if ($user->hasRight('stock', 'creer')) {
877 print '<td class="center"><a href="'.DOL_URL_ROOT.'/product/stock/product.php?dwid='.$object->id.'&id='.$objp->rowid.'&action=correction&token='.newToken().'&backtopage='.urlencode($_SERVER["PHP_SELF"].'?id='.$id).'">';
878 print img_picto($langs->trans("CorrectStock"), 'add', 'class="hideonsmartphone pictofixedwidth" style="color: #a69944"');
879 print $langs->trans("CorrectStock");
880 print "</a></td>";
881 }
882
883 $parameters = array('context' => 'warehousecard', 'obj' => $objp, 'totalarray' => &$totalarray);
884 $reshook = $hookmanager->executeHooks('printFieldListValue', $parameters); // Note that $action and $object may have been modified by hook
885 print $hookmanager->resPrint;
886
887 print "</tr>";
888
889 // Define $unit and $sameunits
890 if (getDolGlobalString('PRODUCT_USE_UNITS')) {
891 if ($i == 0) {
892 $units = $productstatic->fk_unit;
893 } elseif ($productstatic->fk_unit != $units) {
894 $sameunits = false;
895 }
896 }
897
898 $i++;
899 }
900 $db->free($resql);
901
902 $totalarray['val']['totalunit'] = $totalunit;
903 $totalarray['val']['totalvalue'] = price2num($totalvalue, 'MT');
904 $totalarray['val']['totalvaluesell'] = price2num($totalvaluesell, 'MT');
905 $totalarray['val']['units'] = $productstatic->getLabelOfUnit('long', $langs);
906
907 $parameters = array('context' => 'warehousecard', 'totalarray' => &$totalarray);
908 // Note that $action and $object may have been modified by hook
909 $reshook = $hookmanager->executeHooks('printFieldListTotal', $parameters, $object);
910 if ($reshook < 0) {
911 setEventMessages($hookmanager->error, $hookmanager->errors);
912 }
913
914 // Show total line
915 include DOL_DOCUMENT_ROOT.'/core/tpl/list_print_total.tpl.php';
916 } else {
917 dol_print_error($db);
918 }
919 print "</table>";
920 print '</div>';
921 }
922
923
924 // Edit mode
925 if ($action == 'edit' || $action == 're-edit') {
926 $langs->trans("WarehouseEdit");
927
928 print '<form action="card.php" method="POST">';
929 print '<input type="hidden" name="token" value="'.newToken().'">';
930 print '<input type="hidden" name="action" value="update">';
931 print '<input type="hidden" name="id" value="'.$object->id.'">';
932
933 $head = stock_prepare_head($object);
934
935 print dol_get_fiche_head($head, 'card', $langs->trans("Warehouse"), 0, 'stock');
936
937 print '<table class="border centpercent">';
938
939 // Ref
940 print '<tr><td class="titlefieldcreate fieldrequired">'.$langs->trans("Ref").'</td><td><input name="libelle" size="20" value="'.$object->label.'"></td></tr>';
941
942 print '<tr><td>'.$langs->trans("LocationSummary").'</td><td><input name="lieu" class="minwidth300" value="'.$object->lieu.'"></td></tr>';
943
944 // Parent entrepot
945 print '<tr><td>'.$langs->trans("AddIn").'</td><td>';
946 print $formproduct->selectWarehouses($object->fk_parent, 'fk_parent', '', 1);
947 print '</td></tr>';
948
949 // Project
950 if (isModEnabled('project') && $formproject !== null) {
951 $projectid = $object->fk_project;
952 $langs->load('projects');
953 print '<tr><td>'.$langs->trans('Project').'</td><td colspan="2">';
954 print img_picto('', 'project', 'class="pictofixedwidth"').$formproject->select_projects(($socid > 0 ? $socid : -1), (string) $projectid, 'projectid', 0, 0, 1, 1, 0, 0, 0, '', 1, 0, 'maxwidth500');
955 print ' <a href="'.DOL_URL_ROOT.'/projet/card.php?socid='.($socid > 0 ? $socid : "").'&action=create&status=1&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create'.($socid > 0 ? '&socid='.$socid : "")).'"><span class="fa fa-plus-circle valignmiddle" title="'.$langs->trans("AddProject").'"></span></a>';
956 print '</td></tr>';
957 }
958
959 // Description
960 print '<tr><td class="tdtop">'.$langs->trans("Description").'</td><td>';
961 // Editeur wysiwyg
962 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
963 $doleditor = new DolEditor('desc', $object->description, '', 180, 'dolibarr_notes', 'In', false, true, isModEnabled('fckeditor'), ROWS_5, '90%');
964 $doleditor->Create();
965 print '</td></tr>';
966
967 print '<tr><td>'.$langs->trans('Address').'</td><td><textarea name="address" class="quatrevingtpercent" rows="3" wrap="soft">';
968 print $object->address;
969 print '</textarea></td></tr>';
970
971 // Zip / Town
972 print '<tr><td>'.$langs->trans('Zip').'</td><td>';
973 print $formcompany->select_ziptown($object->zip, 'zipcode', array('town', 'selectcountry_id', 'state_id'), 6);
974 print '</td></tr>';
975 print '<tr><td>'.$langs->trans('Town').'</td><td>';
976 print $formcompany->select_ziptown($object->town, 'town', array('zipcode', 'selectcountry_id', 'state_id'));
977 print '</td></tr>';
978
979 // Country
980 print '<tr><td>'.$langs->trans('Country').'</td><td>';
981 print img_picto('', 'globe-americas', 'class="pictofixedwidth"');
982 print $form->select_country($object->country_id ? $object->country_id : $mysoc->country_code, 'country_id');
983 if ($user->admin) {
984 print info_admin($langs->trans("YouCanChangeValuesForThisListFromDictionarySetup"), 1);
985 }
986 print '</td></tr>';
987
988 // Phone / Fax
989 print '<tr><td class="titlefieldcreate">'.$form->editfieldkey('Phone', 'phone', '', $object, 0).'</td><td>';
990 print img_picto('', 'object_phoning', 'class="pictofixedwidth"');
991 print '<input name="phone" size="20" value="'.$object->phone.'"></td></tr>';
992 print '<tr><td class="titlefieldcreate">'.$form->editfieldkey('Fax', 'fax', '', $object, 0).'</td><td>';
993 print img_picto('', 'object_phoning_fax', 'class="pictofixedwidth"');
994 print '<input name="fax" size="20" value="'.$object->fax.'"></td></tr>';
995
996 // Status
997 print '<tr><td>'.$langs->trans("Status").'</td><td>';
998 print '<select id="warehousestatus" name="statut" class="flat">';
999 foreach ($object->labelStatus as $key => $value) {
1000 if ($key == $object->statut) {
1001 print '<option value="'.$key.'" selected>'.$langs->trans($value).'</option>';
1002 } else {
1003 print '<option value="'.$key.'">'.$langs->trans($value).'</option>';
1004 }
1005 }
1006 print '</select>';
1007 print ajax_combobox('warehousestatus');
1008
1009 print '</td></tr>';
1010
1011 // Other attributes
1012 $parameters = array('context' => 'warehousecard', 'colspan' => ' colspan="3"', 'cols' => '3');
1013 $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1014 print $hookmanager->resPrint;
1015 if (empty($reshook)) {
1016 print $object->showOptionals($extrafields, 'edit', $parameters);
1017 }
1018
1019 // Tags-Categories
1020 if (isModEnabled('category')) {
1021 print '<tr><td class="tdtop">'.$langs->trans("Categories").'</td><td colspan="3">';
1022 print $form->selectCategories(Categorie::TYPE_WAREHOUSE, 'categories', $object);
1023 print "</td></tr>";
1024 }
1025
1026 print '</table>';
1027
1028 print dol_get_fiche_end();
1029
1030 print $form->buttonsSaveCancel();
1031
1032 print '</form>';
1033 }
1034 }
1035}
1036
1037/*
1038 * Documents generated
1039 */
1040
1041$modulepart = 'stock';
1042
1043if ($action != 'create' && $action != 'edit' && $action != 'delete') {
1044 print '<br>';
1045 print '<div class="fichecenter"><div class="fichehalfleft">';
1046 print '<a name="builddoc"></a>'; // ancre
1047
1048 // Documents
1049 $objectref = dol_sanitizeFileName($object->ref);
1050 $relativepath = $object->ref.'/'.$objectref.'.pdf';
1051 $filedir = $conf->stock->dir_output.'/'.$objectref;
1052 $urlsource = $_SERVER["PHP_SELF"]."?id=".$object->id;
1053 $genallowed = $usercanread;
1054 $delallowed = $usercancreate;
1055 $modulepart = 'stock';
1056
1057 print $formfile->showdocuments($modulepart, $objectref, $filedir, $urlsource, $genallowed, $delallowed, $object->model_pdf, 0, 0, 0, 28, 0, '', '', '', '', '', $object);
1058 $somethingshown = $formfile->numoffiles;
1059
1060 print '</div><div class="fichehalfright">';
1061
1062 $MAXEVENT = 10;
1063
1064 $morehtmlcenter = '';
1065 //$morehtmlcenter = dolGetButtonTitle($langs->trans('SeeAll'), '', 'fa fa-bars imgforviewmode', DOL_URL_ROOT.'/product/stock/agenda.php?id='.$object->id);
1066
1067 // List of actions on element
1068 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formactions.class.php';
1069 $formactions = new FormActions($db);
1070 $somethingshown = $formactions->showactions($object, 'stock', 0, 1, '', $MAXEVENT, '', $morehtmlcenter); // Show all action for product
1071
1072 print '</div></div>';
1073}
1074
1075// End of page
1076llxFooter();
1077$db->close();
$id
Support class for third parties, contacts, members, users or resources.
Definition account.php:47
if(! $sortfield) if(! $sortorder) $object
Definition account.php:100
$totalarray
Definition export.php:1216
ajax_combobox($htmlname, $events=array(), $minLengthToAutocomplete=0, $forcefocus=0, $widthTypeOfAutocomplete='resolve', $idforemptyvalue='-1', $morecss='')
Convert a html select field into an ajax combobox.
Definition ajax.lib.php:475
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
Definition wrapper.php:91
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:73
Class to manage a WYSIWYG editor.
Class to manage warehouses.
Class to manage standard extra fields.
Class to manage building of HTML components.
Class to build HTML component for third parties management Only common components are here.
Class to offer components to list and upload files.
Class to manage generation of HTML components Only common components must be here.
Class with static methods for building HTML components related to products Only components common to ...
Class to manage building of HTML components.
Class to manage products or services.
Class to manage projects.
global $mysoc
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0, $attop=0)
Set event messages in dol_events session object.
print_liste_field_titre($name, $file="", $field="", $begin="", $param="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $tooltip="", $forcenowrapcolumntitle=0)
Show title line of an array.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2, $allowothertags=array())
Show picto whatever it's its name (generic function)
img_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='', $dragdropfile=0, $morecssdiv='')
Show tabs of a record.
price2num($amount, $rounding='', $option=0)
Function that return a number with universal decimal format (decimal separator is '.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
dol_eval($s, $returnvalue=1, $hideerrors=1, $onlysimplestring='1')
Replace eval function to add more security.
dol_sanitizeFileName($str, $newstr='_', $unaccent=1, $includequotes=0, $allowdash=0)
Clean a string to use it as a file name.
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_set_focus($selector)
Set focus onto field with selector (similar behaviour of 'autofocus' HTML5 tag)
newToken()
Return the value of token currently saved into session with name 'newtoken'.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_clone($srcobject, $native=2)
Create a clone of instance of object (new instance with same value for each properties) With native =...
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false, $decorate=0)
Output date in a string format according to outputlangs (or langs if not defined).
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
load_fiche_titre($title, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='', $morecssonpicto='widthpictotitle')
Load a title with picto.
dol_htmlentitiesbr($stringtoencode, $nl2brmode=0, $pagecodefrom='UTF-8', $removelasteolbr=1)
This function is called to encode a string into a HTML string but differs from htmlentities because a...
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
isModEnabled($module)
Is Dolibarr module enabled.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin='1', $morecss='hideonsmartphone', $textfordropdown='', $picto='')
Show information in HTML for admin users or standard users.
img_edit($titlealt='default', $float=0, $other='')
Show logo edit/modify fiche.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...
restrictedArea(User $user, $features, $object=0, $tableandshare='', $feature2='', $dbt_keyfield='fk_soc', $dbt_select='rowid', $isdraft=0, $mode=0)
Check permissions of a user to show a page and an object.
stock_prepare_head($object)
Prepare array with list of tabs.
Definition stock.lib.php:31