1<?php 2/* Copyright (C) 2013-2020 Laurent Destailleur <eldy@users.sourceforge.net> 3 * 4 * This program is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation; either version 3 of the License, or 7 * (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program. If not, see <https://www.gnu.org/licenses/>. 16 */ 17 18// variable $listofopplabel and $listofoppstatus should be defined 19 20if (!empty($conf->global->PROJECT_USE_OPPORTUNITIES)) 21{ 22 $sql = "SELECT p.fk_opp_status as opp_status, cls.code, COUNT(p.rowid) as nb, SUM(p.opp_amount) as opp_amount, SUM(p.opp_amount * p.opp_percent) as ponderated_opp_amount"; 23 $sql .= " FROM ".MAIN_DB_PREFIX."projet as p LEFT JOIN ".MAIN_DB_PREFIX."c_lead_status as cls ON p.fk_opp_status = cls.rowid"; // If lead status has been removed, we must show it in stats as unknown 24 $sql .= " WHERE p.entity IN (".getEntity('project').")"; 25 $sql .= " AND p.fk_statut = 1"; // Opend projects only 26 if ($mine || empty($user->rights->projet->all->lire)) $sql .= " AND p.rowid IN (".$projectsListId.")"; 27 if ($socid) $sql .= " AND (p.fk_soc IS NULL OR p.fk_soc = 0 OR p.fk_soc = ".$socid.")"; 28 $sql .= " GROUP BY p.fk_opp_status, cls.code"; 29 $resql = $db->query($sql); 30 31 if ($resql) 32 { 33 $num = $db->num_rows($resql); 34 $i = 0; 35 36 $totalnb = 0; 37 $totaloppnb = 0; 38 $totalamount = 0; 39 $ponderated_opp_amount = 0; 40 $valsnb = array(); 41 $valsamount = array(); 42 $dataseries = array(); 43 // -1=Canceled, 0=Draft, 1=Validated, (2=Accepted/On process not managed for customer orders), 3=Closed (Sent/Received, billed or not) 44 while ($i < $num) 45 { 46 $obj = $db->fetch_object($resql); 47 if ($obj) 48 { 49 $valsnb[$obj->opp_status] = $obj->nb; 50 $valsamount[$obj->opp_status] = $obj->opp_amount; 51 $totalnb += $obj->nb; 52 if ($obj->opp_status) $totaloppnb += $obj->nb; 53 if (!in_array($obj->code, array('WON', 'LOST'))) { 54 $totalamount += $obj->opp_amount; 55 $ponderated_opp_amount += $obj->ponderated_opp_amount; 56 } 57 $total += $obj->nb; 58 } 59 $i++; 60 } 61 $db->free($resql); 62 63 $ponderated_opp_amount = $ponderated_opp_amount / 100; 64 65 print '<div class="div-table-responsive-no-min">'; 66 print '<table class="noborder nohover centpercent">'; 67 print '<tr class="liste_titre"><th colspan="2">'.$langs->trans("Statistics").' - '.$langs->trans("OpportunitiesStatusForOpenedProjects").'</th></tr>'."\n"; 68 69 $listofstatus = array_keys($listofoppstatus); 70 // Complete with values found into database and not into the dictionary 71 foreach ($valsamount as $key => $val) { 72 if (!in_array($key, $listofstatus) && $key) { 73 $listofstatus[] = $key; 74 } 75 } 76 77 foreach ($listofstatus as $status) 78 { 79 $labelStatus = ''; 80 81 $code = dol_getIdFromCode($db, $status, 'c_lead_status', 'rowid', 'code'); 82 if ($code) $labelStatus = $langs->transnoentitiesnoconv("OppStatus".$code); 83 if (empty($labelStatus)) $labelStatus = $listofopplabel[$status]; 84 if (empty($labelStatus)) $labelStatus = $langs->transnoentitiesnoconv('OldValue', $status); // When id is id of an entry no more in dictionary for example. 85 86 //$labelStatus .= ' ('.$langs->trans("Coeff").': '.price2num($listofoppstatus[$status]).')'; 87 //$labelStatus .= ' - '.price2num($listofoppstatus[$status]).'%'; 88 89 $dataseries[] = array($labelStatus, (isset($valsamount[$status]) ? (float) $valsamount[$status] : 0)); 90 if (!$conf->use_javascript_ajax) 91 { 92 print '<tr class="oddeven">'; 93 print '<td>'.$labelStatus.'</td>'; 94 print '<td class="right"><a href="list.php?statut='.$status.'">'.price((isset($valsamount[$status]) ? (float) $valsamount[$status] : 0), 0, '', 1, -1, -1, $conf->currency).'</a></td>'; 95 print "</tr>\n"; 96 } 97 } 98 if ($conf->use_javascript_ajax) 99 { 100 print '<tr><td class="center nopaddingleftimp nopaddingrightimp" colspan="2">'; 101 102 include_once DOL_DOCUMENT_ROOT.'/core/class/dolgraph.class.php'; 103 $dolgraph = new DolGraph(); 104 $dolgraph->SetData($dataseries); 105 $dolgraph->SetDataColor(array_values($colorseries)); 106 $dolgraph->setShowLegend(2); 107 $dolgraph->setShowPercent(1); 108 $dolgraph->SetType(array('pie')); 109 //$dolgraph->setWidth('100%'); 110 $dolgraph->SetHeight('200'); 111 $dolgraph->draw('idgraphstatus'); 112 print $dolgraph->show($totaloppnb ? 0 : 1); 113 114 print '</td></tr>'; 115 } 116 //if ($totalinprocess != $total) 117 //print '<tr class="liste_total"><td>'.$langs->trans("Total").' ('.$langs->trans("CustomersOrdersRunning").')</td><td class="right">'.$totalinprocess.'</td></tr>'; 118 print '<tr class="liste_total"><td class="maxwidth200 tdoverflow">'.$langs->trans("OpportunityTotalAmount").' ('.$langs->trans("WonLostExcluded").')</td><td class="right">'.price($totalamount, 0, '', 1, -1, -1, $conf->currency).'</td></tr>'; 119 print '<tr class="liste_total"><td class="minwidth200 tdoverflow">'; 120 //print $langs->trans("OpportunityPonderatedAmount").' ('.$langs->trans("WonLostExcluded").')'; 121 print $form->textwithpicto($langs->trans("OpportunityPonderatedAmount").' ('.$langs->trans("WonLostExcluded").')', $langs->trans("OpportunityPonderatedAmountDesc"), 1); 122 print '</td><td class="right">'.price(price2num($ponderated_opp_amount, 'MT'), 0, '', 1, -1, -1, $conf->currency).'</td></tr>'; 123 print "</table>"; 124 print "</div>"; 125 126 print "<br>"; 127 } else { 128 dol_print_error($db); 129 } 130} 131