dolibarr 21.0.3
box_graph_product_distribution.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2013-2015 Laurent Destailleur <eldy@users.sourceforge.net>
3 * Copyright (C) 2018-2024 Frédéric France <frederic.france@free.fr>
4 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <https://www.gnu.org/licenses/>.
18 */
19
25include_once DOL_DOCUMENT_ROOT.'/core/boxes/modules_boxes.php';
26include_once DOL_DOCUMENT_ROOT.'/core/class/dolgraph.class.php';
27
32{
33 public $boxcode = "productdistribution";
34 public $boximg = "object_product";
35 public $boxlabel = "BoxProductDistribution";
36 public $depends = array("product|service", "facture|propal|commande");
37
38 public $widgettype = 'graph';
39
46 public function __construct($db, $param)
47 {
48 global $user;
49
50 $this->db = $db;
51
52 $this->hidden = !(
53 (isModEnabled('invoice') && $user->hasRight('facture', 'lire'))
54 || (isModEnabled('order') && $user->hasRight('commande', 'lire'))
55 || (isModEnabled('propal') && $user->hasRight('propal', 'lire'))
56 );
57 }
58
65 public function loadBox($max = 5)
66 {
67 global $conf, $user, $langs;
68
69 $this->max = $max;
70 $dir = $conf->user->dir_temp;
71
72 $refreshaction = 'refresh_'.$this->boxcode;
73
74 include_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
75 include_once DOL_DOCUMENT_ROOT.'/comm/propal/class/propal.class.php';
76 include_once DOL_DOCUMENT_ROOT.'/commande/class/commande.class.php';
77
78 $param_year = 'DOLUSER_box_'.$this->boxcode.'_year';
79 $param_showinvoicenb = 'DOLUSER_box_'.$this->boxcode.'_showinvoicenb';
80 $param_showpropalnb = 'DOLUSER_box_'.$this->boxcode.'_showpropalnb';
81 $param_showordernb = 'DOLUSER_box_'.$this->boxcode.'_showordernb';
82 $autosetarray = preg_split("/[,;:]+/", GETPOST('DOL_AUTOSET_COOKIE'));
83 if (in_array('DOLUSER_box_'.$this->boxcode, $autosetarray)) {
84 $year = GETPOSTINT($param_year);
85 $showinvoicenb = GETPOST($param_showinvoicenb, 'alpha');
86 $showpropalnb = GETPOST($param_showpropalnb, 'alpha');
87 $showordernb = GETPOST($param_showordernb, 'alpha');
88 } else {
89 $tmparray = (!empty($_COOKIE['DOLUSER_box_'.$this->boxcode]) ? json_decode($_COOKIE['DOLUSER_box_'.$this->boxcode], true) : array());
90 $year = (!empty($tmparray['year']) ? $tmparray['year'] : '');
91 $showinvoicenb = (!empty($tmparray['showinvoicenb']) ? $tmparray['showinvoicenb'] : '');
92 $showpropalnb = (!empty($tmparray['showpropalnb']) ? $tmparray['showpropalnb'] : '');
93 $showordernb = (!empty($tmparray['showordernb']) ? $tmparray['showordernb'] : '');
94 }
95 if (empty($showinvoicenb) && empty($showpropalnb) && empty($showordernb)) {
96 $showpropalnb = 1;
97 $showinvoicenb = 1;
98 $showordernb = 1;
99 }
100 if (!isModEnabled('invoice') || !$user->hasRight('facture', 'lire')) {
101 $showinvoicenb = 0;
102 }
103 if (isModEnabled('propal') || !$user->hasRight('propal', 'lire')) {
104 $showpropalnb = 0;
105 }
106 if (!isModEnabled('order') || !$user->hasRight('commande', 'lire')) {
107 $showordernb = 0;
108 }
109
110 $nowarray = dol_getdate(dol_now(), true);
111 if (empty($year)) {
112 $year = $nowarray['year'];
113 }
114
115 $nbofgraph = 0;
116 if ($showinvoicenb) {
117 $nbofgraph++;
118 }
119 if ($showpropalnb) {
120 $nbofgraph++;
121 }
122 if ($showordernb) {
123 $nbofgraph++;
124 }
125
126 $text = $langs->trans("BoxProductDistribution", $max).' - '.$langs->trans("Year").': '.$year;
127 $this->info_box_head = array(
128 'text' => $text,
129 'limit' => dol_strlen($text),
130 'graph' => 1,
131 'sublink' => '',
132 'subtext' => $langs->trans("Filter"),
133 'subpicto' => 'filter.png',
134 'subclass' => 'linkobject boxfilter',
135 'target' => 'none' // Set '' to get target="_blank"
136 );
137
138
139 $socid = empty($user->socid) ? 0 : $user->socid;
140 $mesg = '';
141 $px1 = null;
142 $px2 = null;
143 $px3 = null;
144 $userid = 0; // No filter on user creation
145
146 $WIDTH = ($nbofgraph >= 2 || !empty($conf->dol_optimize_smallscreen)) ? '300' : '320';
147 $HEIGHT = '150'; // Height require to have 5+1 entries into legend visible.
148
149 if (isModEnabled("propal") && $user->hasRight('propal', 'lire')) {
150 // Build graphic number of object. $data = array(array('Lib',val1,val2,val3),...)
151 if ($showpropalnb) {
152 $langs->load("propal");
153 include_once DOL_DOCUMENT_ROOT.'/comm/propal/class/propalestats.class.php';
154
155 $showpointvalue = 1;
156 $nocolor = 0;
157 $stats_proposal = new PropaleStats($this->db, $socid, ($userid > 0 ? $userid : 0));
158 $data2 = $stats_proposal->getAllByProductEntry($year, (GETPOST('action', 'aZ09') == $refreshaction ? -1 : (3600 * 24)), $max);
159 if (empty($data2)) {
160 $showpointvalue = 0;
161 $nocolor = 1;
162 $data2 = array(array(0 => $langs->trans("None"), 1 => 1));
163 }
164
165 $filenamenb = $dir."/prodserforpropal-".$year.".png";
166 $fileurlnb = DOL_URL_ROOT.'/viewimage.php?modulepart=proposalstats&amp;file=prodserforpropal-'.$year.'.png';
167
168 $px2 = new DolGraph();
169 $mesg = $px2->isGraphKo();
170 if (!$mesg) {
171 $i = 0;
172 $legend = array();
173
174 // Truncate length of legend
175 foreach ($data2 as $key => $val) {
176 $data2[$key][0] = dol_trunc($data2[$key][0], 32);
177 $legend[] = $data2[$key][0];
178 $i++;
179 }
180
181 $px2->SetData($data2);
182 unset($data2);
183
184 if ($nocolor) {
185 $px2->SetDataColor(array(array(220, 220, 220)));
186 }
187 $px2->SetLegend($legend);
188 $px2->setShowLegend(2);
189 if (!empty($conf->dol_optimize_smallscreen)) {
190 $px2->SetWidth(320);
191 }
192 $px2->setShowPointValue($showpointvalue);
193 $px2->setShowPercent(0);
194 $px2->SetMaxValue($px2->GetCeilMaxValue());
195 $px2->SetWidth($WIDTH);
196 $px2->SetHeight($HEIGHT);
197 //$px2->SetYLabel($langs->trans("AmountOfBillsHT"));
198 $px2->SetShading(3);
199 $px2->SetHorizTickIncrement(1);
200 $px2->SetCssPrefix("cssboxes");
201 //$px2->mode='depth';
202 $px2->SetType(array('pie'));
203 $px2->SetTitle($langs->trans("ForObject", $langs->transnoentitiesnoconv("Proposals")));
204 $px2->combine = 0.05;
205
206 $px2->draw($filenamenb, $fileurlnb);
207 }
208 }
209 }
210
211 if (isModEnabled('order') && $user->hasRight('commande', 'lire')) {
212 // Build graphic number of object. $data = array(array('Lib',val1,val2,val3),...)
213 if ($showordernb) {
214 $langs->load("orders");
215 include_once DOL_DOCUMENT_ROOT.'/commande/class/commandestats.class.php';
216
217 $showpointvalue = 1;
218 $nocolor = 0;
219 $mode = 'customer';
220 $stats_order = new CommandeStats($this->db, $socid, $mode, ($userid > 0 ? $userid : 0));
221 $data3 = $stats_order->getAllByProductEntry($year, (GETPOST('action', 'aZ09') == $refreshaction ? -1 : (3600 * 24)), $max);
222 if (empty($data3)) {
223 $showpointvalue = 0;
224 $nocolor = 1;
225
226 $data3 = array(array(0 => $langs->trans("None"), 1 => 1));
227 }
228
229 $filenamenb = $dir."/prodserfororder-".$year.".png";
230 $fileurlnb = DOL_URL_ROOT.'/viewimage.php?modulepart=orderstats&amp;file=prodserfororder-'.$year.'.png';
231
232 $px3 = new DolGraph();
233 $mesg = $px3->isGraphKo();
234 if (!$mesg) {
235 $i = 0;
236 $legend = array();
237
238 // Truncate length of legend
239 foreach ($data3 as $key => $val) {
240 $data3[$key][0] = dol_trunc($data3[$key][0], 32);
241 $legend[] = $data3[$key][0];
242 $i++;
243 }
244
245 $px3->SetData($data3);
246 unset($data3);
247
248 if ($nocolor) {
249 $px3->SetDataColor(array(array(220, 220, 220)));
250 }
251 $px3->SetLegend($legend);
252 $px3->setShowLegend(2);
253 if (!empty($conf->dol_optimize_smallscreen)) {
254 $px3->SetWidth(320);
255 }
256 $px3->setShowPointValue($showpointvalue);
257 $px3->setShowPercent(0);
258 $px3->SetMaxValue($px3->GetCeilMaxValue());
259 $px3->SetWidth($WIDTH);
260 $px3->SetHeight($HEIGHT);
261 //$px3->SetYLabel($langs->trans("AmountOfBillsHT"));
262 $px3->SetShading(3);
263 $px3->SetHorizTickIncrement(1);
264 $px3->SetCssPrefix("cssboxes");
265 //$px3->mode='depth';
266 $px3->SetType(array('pie'));
267 $px3->SetTitle($langs->trans("ForObject", $langs->transnoentitiesnoconv("Orders")));
268 $px3->combine = 0.05;
269
270 $px3->draw($filenamenb, $fileurlnb);
271 }
272 }
273 }
274
275
276 if (isModEnabled('invoice') && $user->hasRight('facture', 'lire')) {
277 // Build graphic number of object. $data = array(array('Lib',val1,val2,val3),...)
278 if ($showinvoicenb) {
279 $langs->load("bills");
280 include_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facturestats.class.php';
281
282 $showpointvalue = 1;
283 $nocolor = 0;
284 $mode = 'customer';
285 $stats_invoice = new FactureStats($this->db, $socid, $mode, ($userid > 0 ? $userid : 0));
286 $data1 = $stats_invoice->getAllByProductEntry($year, (GETPOST('action', 'aZ09') == $refreshaction ? -1 : (3600 * 24)), $max);
287
288 if (empty($data1)) {
289 $showpointvalue = 0;
290 $nocolor = 1;
291 $data1 = array(array(0 => $langs->trans("None"), 1 => 1));
292 }
293 $filenamenb = $dir."/prodserforinvoice-".$year.".png";
294 $fileurlnb = DOL_URL_ROOT.'/viewimage.php?modulepart=productstats&amp;file=prodserforinvoice-'.$year.'.png';
295
296 $px1 = new DolGraph();
297 $mesg = $px1->isGraphKo();
298 if (!$mesg) {
299 $i = 0;
300 $legend = array();
301
302 // Truncate length of legend
303 foreach ($data1 as $key => $val) {
304 $data1[$key][0] = dol_trunc($data1[$key][0], 32);
305 $legend[] = $data1[$key][0];
306 $i++;
307 }
308
309 $px1->SetData($data1);
310 unset($data1);
311
312 if ($nocolor) {
313 $px1->SetDataColor(array(array(220, 220, 220)));
314 }
315 $px1->SetLegend($legend);
316 $px1->setShowLegend(2);
317 if (!empty($conf->dol_optimize_smallscreen)) {
318 $px1->SetWidth(320);
319 }
320 $px1->setShowPointValue($showpointvalue);
321 $px1->setShowPercent(0);
322 $px1->SetMaxValue($px1->GetCeilMaxValue());
323 $px1->SetWidth($WIDTH);
324 $px1->SetHeight($HEIGHT);
325 //$px1->SetYLabel($langs->trans("NumberOfBills"));
326 $px1->SetShading(3);
327 $px1->SetHorizTickIncrement(1);
328 $px1->SetCssPrefix("cssboxes");
329 //$px1->mode='depth';
330 $px1->SetType(array('pie'));
331 $px1->SetTitle($langs->trans("ForObject", $langs->transnoentitiesnoconv("Invoices")));
332 $px1->combine = 0.05;
333
334 $px1->draw($filenamenb, $fileurlnb);
335 }
336 }
337 }
338
339 if (empty($nbofgraph)) {
340 $langs->load("errors");
341 $mesg = $langs->trans("ReadPermissionNotAllowed");
342 }
343 if (empty($conf->use_javascript_ajax)) {
344 $langs->load("errors");
345 $mesg = $langs->trans("WarningFeatureDisabledWithDisplayOptimizedForBlindNoJs");
346 }
347
348 if (!$mesg) {
349 $stringtoshow = '';
350 $stringtoshow .= '<script nonce="'.getNonce().'" type="text/javascript">
351 jQuery(document).ready(function() {
352 jQuery("#idsubimg'.$this->boxcode.'").click(function() {
353 jQuery("#idfilter'.$this->boxcode.'").toggle();
354 });
355 });
356 </script>';
357 $stringtoshow .= '<div class="center hideobject" id="idfilter'.$this->boxcode.'">'; // hideobject is to start hidden
358 $stringtoshow .= '<form class="flat formboxfilter" method="POST" action="'.$_SERVER["PHP_SELF"].'">';
359 $stringtoshow .= '<input type="hidden" name="token" value="'.newToken().'">';
360 $stringtoshow .= '<input type="hidden" name="action" value="'.$refreshaction.'">';
361 $stringtoshow .= '<input type="hidden" name="page_y" value="">';
362 $stringtoshow .= '<input type="hidden" name="DOL_AUTOSET_COOKIE" value="DOLUSER_box_'.$this->boxcode.':year,showinvoicenb,showpropalnb,showordernb">';
363 if (isModEnabled("propal") || $user->hasRight('propal', 'lire')) {
364 $stringtoshow .= '<input type="checkbox" name="'.$param_showpropalnb.'"'.($showpropalnb ? ' checked' : '').'> '.$langs->trans("ForProposals");
365 $stringtoshow .= '&nbsp;';
366 }
367 if (isModEnabled('order') || $user->hasRight('commande', 'lire')) {
368 $stringtoshow .= '<input type="checkbox" name="'.$param_showordernb.'"'.($showordernb ? ' checked' : '').'> '.$langs->trans("ForCustomersOrders");
369 }
370 if (isModEnabled('invoice') || $user->hasRight('facture', 'lire')) {
371 $stringtoshow .= '<input type="checkbox" name="'.$param_showinvoicenb.'"'.($showinvoicenb ? ' checked' : '').'> '.$langs->trans("ForCustomersInvoices");
372 $stringtoshow .= ' &nbsp; ';
373 }
374 $stringtoshow .= '<br>';
375 $stringtoshow .= $langs->trans("Year").' <input class="flat" size="4" type="text" name="'.$param_year.'" value="'.$year.'">';
376 $stringtoshow .= '<input type="image" class="reposition inline-block valigntextbottom" alt="'.$langs->trans("Refresh").'" src="'.img_picto('', 'refresh.png', '', 0, 1).'">';
377 $stringtoshow .= '</form>';
378 $stringtoshow .= '</div>';
379
380 if ($nbofgraph == 1) {
381 if ($showpropalnb && $px2 !== null) {
382 $stringtoshow .= $px2->show();
383 } elseif ($showordernb && $px3 !== null) {
384 $stringtoshow .= $px3->show();
385 } elseif ($px1 !== null) {
386 $stringtoshow .= $px1->show();
387 }
388 }
389 if ($nbofgraph == 2) {
390 $stringtoshow .= '<div class="fichecenter"><div class="containercenter"><div class="fichehalfleft">';
391 if (isModEnabled('propal') && $showpropalnb && $px2 !== null) {
392 $stringtoshow .= $px2->show();
393 } elseif (isModEnabled('order') && $showordernb && $px3 !== null) {
394 $stringtoshow .= $px3->show();
395 }
396 $stringtoshow .= '</div><div class="fichehalfright">';
397 if (isModEnabled('invoice') && $showinvoicenb && $px1 !== null) {
398 $stringtoshow .= $px1->show();
399 } elseif (isModEnabled('order') && $showordernb && $px3 !== null) {
400 $stringtoshow .= $px3->show();
401 }
402 $stringtoshow .= '</div></div></div>';
403 }
404 if ($nbofgraph == 3 && $px1 !== null && $px2 !== null && $px3 !== null) {
405 $stringtoshow .= '<div class="fichecenter"><div class="containercenter"><div class="fichehalfleft">';
406 $stringtoshow .= $px2->show();
407 $stringtoshow .= '</div><div class="fichehalfright">';
408 $stringtoshow .= $px3->show();
409 $stringtoshow .= '</div></div></div>';
410 $stringtoshow .= '<div class="fichecenter"><div class="containercenter">';
411 $stringtoshow .= $px1->show();
412 $stringtoshow .= '</div></div>';
413 }
414 $this->info_box_contents[0][0] = array(
415 'tr' => 'class="oddeven nohover"',
416 'td' => 'class="nohover center"',
417 'textnoformat' => $stringtoshow,
418 );
419 } else {
420 $this->info_box_contents[0][0] = array(
421 'td' => 'class="nohover left"',
422 'maxlength' => 500,
423 'text' => '<span class="opacitymedium">'.$mesg.'</span>'
424 );
425 }
426 }
427
428
429
438 public function showBox($head = null, $contents = null, $nooutput = 0)
439 {
440 return parent::showBox($this->info_box_head, $this->info_box_contents, $nooutput);
441 }
442}
Class to manage order statistics (customer and supplier)
Class to build graphs.
Class to manage stats for invoices (customer and supplier)
Class ModeleBoxes.
Class to manage proposals statistics.
Class to manage the box to show last invoices.
showBox($head=null, $contents=null, $nooutput=0)
Method to show box.
loadBox($max=5)
Load data into info_box_contents array to show array later.
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)
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dol_strlen($string, $stringencoding='UTF-8')
Make a strlen call.
dol_now($mode='auto')
Return date for now.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_trunc($string, $size=40, $trunc='right', $stringencoding='UTF-8', $nodot=0, $display=0)
Truncate a string to a particular length adding '…' if string larger than length.
dol_getdate($timestamp, $fast=false, $forcetimezone='')
Return an array with locale date info.
global $conf
The following vars must be defined: $type2label $form $conf, $lang, The following vars may also be de...
Definition member.php:79