1 | <?php |
||
2 | |||
3 | /* Copyright (C) 2001-2004 Rodolphe Quiedeville <[email protected]> |
||
4 | * Copyright (C) 2004-2020 Laurent Destailleur <[email protected]> |
||
5 | * Copyright (C) 2005-2010 Regis Houssin <[email protected]> |
||
6 | * Copyright (C) 2012-2016 Juanjo Menent <[email protected]> |
||
7 | * Copyright (C) 2015-2021 Alexandre Spangaro <[email protected]> |
||
8 | * Copyright (C) 2015 Marcos García <[email protected]> |
||
9 | * Copyright (C) 2016 Josep Lluís Amador <[email protected]> |
||
10 | * Copyright (C) 2021-2023 Gauthier VERDOL <[email protected]> |
||
11 | * Copyright (C) 2021 Noé Cendrier <[email protected]> |
||
12 | * Copyright (C) 2023 Frédéric France <[email protected]> |
||
13 | * Copyright (C) 2024 MDW <[email protected]> |
||
14 | * Copyright (C) 2024 Frédéric France <[email protected]> |
||
15 | * Copyright (C) 2024 Rafael San José <[email protected]> |
||
16 | * |
||
17 | * This program is free software; you can redistribute it and/or modify |
||
18 | * it under the terms of the GNU General Public License as published by |
||
19 | * the Free Software Foundation; either version 3 of the License, or |
||
20 | * (at your option) any later version. |
||
21 | * |
||
22 | * This program is distributed in the hope that it will be useful, |
||
23 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
24 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||
25 | * GNU General Public License for more details. |
||
26 | * |
||
27 | * You should have received a copy of the GNU General Public License |
||
28 | * along with this program. If not, see <https://www.gnu.org/licenses/>. |
||
29 | */ |
||
30 | |||
31 | use Dolibarr\Code\Categories\Classes\Categorie; |
||
32 | use Dolibarr\Code\Comm\Classes\Propal; |
||
33 | use Dolibarr\Code\Compta\Classes\Facture; |
||
34 | use Dolibarr\Code\Core\Classes\CommonInvoice; |
||
35 | use Dolibarr\Code\Core\Classes\Form; |
||
36 | use Dolibarr\Code\Core\Classes\FormFile; |
||
37 | use Dolibarr\Code\Core\Classes\FormProjets; |
||
38 | use Dolibarr\Code\EventOrganizaction\Classes\ConferenceOrBoothAttendee; |
||
39 | use Dolibarr\Code\ExpenseReport\Classes\ExpenseReport; |
||
40 | use Dolibarr\Code\Loan\Classes\LoanSchedule; |
||
41 | use Dolibarr\Code\Product\Classes\Product; |
||
42 | use Dolibarr\Code\Projet\Classes\Project; |
||
43 | use Dolibarr\Code\Projet\Classes\Task; |
||
44 | use Dolibarr\Code\User\Classes\User; |
||
45 | use Dolibarr\Lib\Misc; |
||
46 | use Dolibarr\Lib\ViewMain; |
||
47 | |||
48 | /** |
||
49 | * \file htdocs/projet/element.php |
||
50 | * \ingroup projet |
||
51 | * \brief Page of project referrers |
||
52 | */ |
||
53 | |||
54 | // Load Dolibarr environment |
||
55 | require constant('DOL_DOCUMENT_ROOT') . '/main.inc.php'; |
||
56 | require_once constant('DOL_DOCUMENT_ROOT') . '/core/lib/project.lib.php'; |
||
57 | require_once constant('DOL_DOCUMENT_ROOT') . '/core/lib/date.lib.php'; |
||
58 | |||
59 | // Load translation files required by the page |
||
60 | $langs->loadLangs(array('projects', 'companies', 'suppliers', 'compta')); |
||
61 | if (isModEnabled('invoice')) { |
||
62 | $langs->load("bills"); |
||
63 | } |
||
64 | if (isModEnabled('order')) { |
||
65 | $langs->load("orders"); |
||
66 | } |
||
67 | if (isModEnabled("propal")) { |
||
68 | $langs->load("propal"); |
||
69 | } |
||
70 | if (isModEnabled('intervention')) { |
||
71 | $langs->load("interventions"); |
||
72 | } |
||
73 | if (isModEnabled('deplacement')) { |
||
74 | $langs->load("trips"); |
||
75 | } |
||
76 | if (isModEnabled('expensereport')) { |
||
77 | $langs->load("trips"); |
||
78 | } |
||
79 | if (isModEnabled('don')) { |
||
80 | $langs->load("donations"); |
||
81 | } |
||
82 | if (isModEnabled('loan')) { |
||
83 | $langs->load("loan"); |
||
84 | } |
||
85 | if (isModEnabled('salaries')) { |
||
86 | $langs->load("salaries"); |
||
87 | } |
||
88 | if (isModEnabled('mrp')) { |
||
89 | $langs->load("mrp"); |
||
90 | } |
||
91 | if (isModEnabled('eventorganization')) { |
||
92 | $langs->load("eventorganization"); |
||
93 | } |
||
94 | //if (isModEnabled('stocktransfer')) { |
||
95 | // $langs->load("stockstransfer"); |
||
96 | //} |
||
97 | |||
98 | $id = GETPOSTINT('id'); |
||
99 | $ref = GETPOST('ref', 'alpha'); |
||
100 | $action = GETPOST('action', 'aZ09'); |
||
101 | $datesrfc = GETPOST('datesrfc'); // deprecated |
||
102 | $dateerfc = GETPOST('dateerfc'); // deprecated |
||
103 | $dates = dol_mktime(0, 0, 0, GETPOST('datesmonth'), GETPOST('datesday'), GETPOST('datesyear')); |
||
104 | $datee = dol_mktime(23, 59, 59, GETPOST('dateemonth'), GETPOST('dateeday'), GETPOST('dateeyear')); |
||
105 | if (empty($dates) && !empty($datesrfc)) { // deprecated |
||
106 | $dates = dol_stringtotime($datesrfc); |
||
107 | } |
||
108 | if (empty($datee) && !empty($dateerfc)) { // deprecated |
||
109 | $datee = dol_stringtotime($dateerfc); |
||
110 | } |
||
111 | if (!GETPOSTISSET('datesrfc') && !GETPOSTISSET('datesday') && getDolGlobalString('PROJECT_LINKED_ELEMENT_DEFAULT_FILTER_YEAR')) { |
||
112 | $new = dol_now(); |
||
113 | $tmp = dol_getdate($new); |
||
114 | //$datee=$now |
||
115 | //$dates=dol_time_plus_duree($datee, -1, 'y'); |
||
116 | $dates = dol_get_first_day($tmp['year'], 1); |
||
117 | } |
||
118 | if ($id == '' && $ref == '') { |
||
119 | setEventMessage($langs->trans('ErrorBadParameters'), 'errors'); |
||
120 | header('Location: list.php'); |
||
121 | exit(); |
||
122 | } |
||
123 | |||
124 | $mine = GETPOST('mode') == 'mine' ? 1 : 0; |
||
125 | //if (! $user->rights->projet->all->lire) $mine=1; // Special for projects |
||
126 | |||
127 | $object = new Project($db); |
||
128 | |||
129 | include DOL_DOCUMENT_ROOT . '/core/actions_fetchobject.inc.php'; // Must be include, not include_once |
||
130 | if (getDolGlobalString('PROJECT_ALLOW_COMMENT_ON_PROJECT') && method_exists($object, 'fetchComments') && empty($object->comments)) { |
||
131 | $object->fetchComments(); |
||
132 | } |
||
133 | |||
134 | // Security check |
||
135 | $socid = $object->socid; |
||
136 | //if ($user->socid > 0) $socid = $user->socid; // For external user, no check is done on company because readability is managed by public status of project and assignment. |
||
137 | $result = restrictedArea($user, 'projet', $object->id, 'projet&project'); |
||
138 | |||
139 | $hookmanager->initHooks(array('projectOverview')); |
||
140 | |||
141 | |||
142 | /* |
||
143 | * View |
||
144 | */ |
||
145 | |||
146 | $title = $langs->trans('ProjectReferers') . ' - ' . $object->ref . ' ' . $object->name; |
||
147 | if (getDolGlobalString('MAIN_HTML_TITLE') && preg_match('/projectnameonly/', getDolGlobalString('MAIN_HTML_TITLE')) && $object->name) { |
||
148 | $title = $object->ref . ' ' . $object->name . ' - ' . $langs->trans('ProjectReferers'); |
||
149 | } |
||
150 | |||
151 | $help_url = 'EN:Module_Projects|FR:Module_Projets|ES:Módulo_Proyectos|DE:Modul_Projekte'; |
||
152 | |||
153 | ViewMain::llxHeader('', $title, $help_url); |
||
154 | |||
155 | $form = new Form($db); |
||
156 | $formproject = new FormProjets($db); |
||
157 | $formfile = new FormFile($db); |
||
158 | |||
159 | $userstatic = new User($db); |
||
160 | |||
161 | // To verify role of users |
||
162 | $userAccess = $object->restrictedProjectArea($user); |
||
163 | |||
164 | $head = project_prepare_head($object); |
||
165 | print dol_get_fiche_head($head, 'element', $langs->trans("Project"), -1, ($object->public ? 'projectpub' : 'project')); |
||
166 | |||
167 | |||
168 | // Project card |
||
169 | |||
170 | if (!empty($_SESSION['pageforbacktolist']) && !empty($_SESSION['pageforbacktolist']['project'])) { |
||
171 | $tmpurl = $_SESSION['pageforbacktolist']['project']; |
||
172 | $tmpurl = preg_replace('/__SOCID__/', (string)$object->socid, $tmpurl); |
||
173 | $linkback = '<a href="' . $tmpurl . (preg_match('/\?/', $tmpurl) ? '&' : '?') . 'restore_lastsearch_values=1">' . $langs->trans("BackToList") . '</a>'; |
||
174 | } else { |
||
175 | $linkback = '<a href="' . constant('BASE_URL') . '/projet/list.php?restore_lastsearch_values=1">' . $langs->trans("BackToList") . '</a>'; |
||
176 | } |
||
177 | |||
178 | $morehtmlref = '<div class="refidno">'; |
||
179 | // Title |
||
180 | $morehtmlref .= $object->title; |
||
181 | // Thirdparty |
||
182 | if (!empty($object->thirdparty->id) && $object->thirdparty->id > 0) { |
||
183 | $morehtmlref .= '<br>' . $object->thirdparty->getNomUrl(1, 'project'); |
||
0 ignored issues
–
show
|
|||
184 | } |
||
185 | $morehtmlref .= '</div>'; |
||
186 | |||
187 | // Define a complementary filter for search of next/prev ref. |
||
188 | if (!$user->hasRight('projet', 'all', 'lire')) { |
||
189 | $objectsListId = $object->getProjectsAuthorizedForUser($user, 0, 0); |
||
190 | $object->next_prev_filter = "te.rowid IN (" . $db->sanitize(count($objectsListId) ? implode(',', array_keys($objectsListId)) : '0') . ")"; |
||
191 | } |
||
192 | |||
193 | dol_banner_tab($object, 'ref', $linkback, 1, 'ref', 'ref', $morehtmlref); |
||
194 | |||
195 | |||
196 | print '<div class="fichecenter">'; |
||
197 | print '<div class="fichehalfleft">'; |
||
198 | print '<div class="underbanner clearboth"></div>'; |
||
199 | |||
200 | print '<table class="border tableforfield centpercent">'; |
||
201 | |||
202 | // Usage |
||
203 | if (getDolGlobalString('PROJECT_USE_OPPORTUNITIES') || !getDolGlobalString('PROJECT_HIDE_TASKS') || isModEnabled('eventorganization')) { |
||
204 | print '<tr><td class="tdtop">'; |
||
205 | print $langs->trans("Usage"); |
||
206 | print '</td>'; |
||
207 | print '<td>'; |
||
208 | if (getDolGlobalString('PROJECT_USE_OPPORTUNITIES')) { |
||
209 | print '<input type="checkbox" disabled name="usage_opportunity"' . (GETPOSTISSET('usage_opportunity') ? (GETPOST('usage_opportunity', 'alpha') != '' ? ' checked="checked"' : '') : ($object->usage_opportunity ? ' checked="checked"' : '')) . '"> '; |
||
210 | $htmltext = $langs->trans("ProjectFollowOpportunity"); |
||
211 | print $form->textwithpicto($langs->trans("ProjectFollowOpportunity"), $htmltext); |
||
212 | print '<br>'; |
||
213 | } |
||
214 | if (!getDolGlobalString('PROJECT_HIDE_TASKS')) { |
||
215 | print '<input type="checkbox" disabled name="usage_task"' . (GETPOSTISSET('usage_task') ? (GETPOST('usage_task', 'alpha') != '' ? ' checked="checked"' : '') : ($object->usage_task ? ' checked="checked"' : '')) . '"> '; |
||
216 | $htmltext = $langs->trans("ProjectFollowTasks"); |
||
217 | print $form->textwithpicto($langs->trans("ProjectFollowTasks"), $htmltext); |
||
218 | print '<br>'; |
||
219 | } |
||
220 | if (!getDolGlobalString('PROJECT_HIDE_TASKS') && getDolGlobalString('PROJECT_BILL_TIME_SPENT')) { |
||
221 | print '<input type="checkbox" disabled name="usage_bill_time"' . (GETPOSTISSET('usage_bill_time') ? (GETPOST('usage_bill_time', 'alpha') != '' ? ' checked="checked"' : '') : ($object->usage_bill_time ? ' checked="checked"' : '')) . '"> '; |
||
222 | $htmltext = $langs->trans("ProjectBillTimeDescription"); |
||
223 | print $form->textwithpicto($langs->trans("BillTime"), $htmltext); |
||
224 | print '<br>'; |
||
225 | } |
||
226 | if (isModEnabled('eventorganization')) { |
||
227 | print '<input type="checkbox" disabled name="usage_organize_event"' . (GETPOSTISSET('usage_organize_event') ? (GETPOST('usage_organize_event', 'alpha') != '' ? ' checked="checked"' : '') : ($object->usage_organize_event ? ' checked="checked"' : '')) . '"> '; |
||
228 | $htmltext = $langs->trans("EventOrganizationDescriptionLong"); |
||
229 | print $form->textwithpicto($langs->trans("ManageOrganizeEvent"), $htmltext); |
||
230 | } |
||
231 | print '</td></tr>'; |
||
232 | } |
||
233 | |||
234 | // Visibility |
||
235 | print '<tr><td class="titlefield">' . $langs->trans("Visibility") . '</td><td>'; |
||
236 | if ($object->public) { |
||
237 | print img_picto($langs->trans('SharedProject'), 'world', 'class="paddingrightonly"'); |
||
238 | print $langs->trans('SharedProject'); |
||
239 | } else { |
||
240 | print img_picto($langs->trans('PrivateProject'), 'private', 'class="paddingrightonly"'); |
||
241 | print $langs->trans('PrivateProject'); |
||
242 | } |
||
243 | print '</td></tr>'; |
||
244 | |||
245 | if (getDolGlobalString('PROJECT_USE_OPPORTUNITIES')) { |
||
246 | // Opportunity status |
||
247 | print '<tr><td>' . $langs->trans("OpportunityStatus") . '</td><td>'; |
||
248 | $code = dol_getIdFromCode($db, $object->opp_status, 'c_lead_status', 'rowid', 'code'); |
||
249 | if ($code) { |
||
250 | print $langs->trans("OppStatus" . $code); |
||
251 | } |
||
252 | print '</td></tr>'; |
||
253 | |||
254 | // Opportunity percent |
||
255 | print '<tr><td>' . $langs->trans("OpportunityProbability") . '</td><td>'; |
||
256 | if (!is_null($object->opp_percent) && strcmp($object->opp_percent, '')) { |
||
257 | print price($object->opp_percent, 0, $langs, 1, 0) . ' %'; |
||
258 | } |
||
259 | print '</td></tr>'; |
||
260 | |||
261 | // Opportunity Amount |
||
262 | print '<tr><td>' . $langs->trans("OpportunityAmount") . '</td><td>'; |
||
263 | if (!is_null($object->opp_amount) && strcmp($object->opp_amount, '')) { |
||
264 | print '<span class="amount">' . price($object->opp_amount, 0, $langs, 1, 0, 0, $conf->currency) . '</span>'; |
||
265 | if (strcmp($object->opp_percent, '')) { |
||
266 | print ' <span title="' . dol_escape_htmltag($langs->trans('OpportunityWeightedAmount')) . '"><span class="opacitymedium">' . $langs->trans("OpportunityWeightedAmountShort") . '</span>: <span class="amount">' . price($object->opp_amount * $object->opp_percent / 100, 0, $langs, 1, 0, -1, $conf->currency) . '</span></span>'; |
||
267 | } |
||
268 | } |
||
269 | print '</td></tr>'; |
||
270 | } |
||
271 | |||
272 | // Budget |
||
273 | print '<tr><td>' . $langs->trans("Budget") . '</td><td>'; |
||
274 | if (!is_null($object->budget_amount) && strcmp($object->budget_amount, '')) { |
||
275 | print '<span class="amount">' . price($object->budget_amount, 0, $langs, 1, 0, 0, $conf->currency) . '</span>'; |
||
276 | } |
||
277 | print '</td></tr>'; |
||
278 | |||
279 | // Date start - end project |
||
280 | print '<tr><td>' . $langs->trans("Dates") . '</td><td>'; |
||
281 | $start = dol_print_date($object->date_start, 'day'); |
||
282 | print($start ? $start : '?'); |
||
283 | $end = dol_print_date($object->date_end, 'day'); |
||
284 | print ' - '; |
||
285 | print($end ? $end : '?'); |
||
286 | if ($object->hasDelay()) { |
||
287 | print img_warning("Late"); |
||
288 | } |
||
289 | print '</td></tr>'; |
||
290 | |||
291 | // Other attributes |
||
292 | $cols = 2; |
||
293 | include DOL_DOCUMENT_ROOT . '/core/tpl/extrafields_view.tpl.php'; |
||
294 | |||
295 | print '</table>'; |
||
296 | |||
297 | print '</div>'; |
||
298 | print '<div class="fichehalfright">'; |
||
299 | print '<div class="underbanner clearboth"></div>'; |
||
300 | |||
301 | print '<table class="border tableforfield centpercent">'; |
||
302 | |||
303 | // Description |
||
304 | print '<td class="titlefield tdtop">' . $langs->trans("Description") . '</td><td>'; |
||
305 | print dol_htmlentitiesbr($object->description); |
||
306 | print '</td></tr>'; |
||
307 | |||
308 | // Categories |
||
309 | if (isModEnabled('category')) { |
||
310 | print '<tr><td class="valignmiddle">' . $langs->trans("Categories") . '</td><td>'; |
||
311 | print $form->showCategories($object->id, Categorie::TYPE_PROJECT, 1); |
||
312 | print "</td></tr>"; |
||
313 | } |
||
314 | |||
315 | print '</table>'; |
||
316 | |||
317 | print '</div>'; |
||
318 | print '</div>'; |
||
319 | |||
320 | print '<div class="clearboth"></div>'; |
||
321 | |||
322 | print dol_get_fiche_end(); |
||
323 | |||
324 | print '<br>'; |
||
325 | |||
326 | /* |
||
327 | * Referrer types |
||
328 | */ |
||
329 | |||
330 | $listofreferent = array( |
||
331 | 'entrepot' => array( |
||
332 | 'name' => "Warehouse", |
||
333 | 'title' => "ListWarehouseAssociatedProject", |
||
334 | 'class' => 'Entrepot', |
||
335 | 'table' => 'entrepot', |
||
336 | 'datefieldname' => 'date_entrepot', |
||
337 | 'urlnew' => constant('BASE_URL') . '/product/stock/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
338 | 'lang' => 'entrepot', |
||
339 | 'buttonnew' => 'AddWarehouse', |
||
340 | 'project_field' => 'fk_project', |
||
341 | 'testnew' => $user->hasRight('stock', 'creer'), |
||
342 | 'test' => isModEnabled('stock') && $user->hasRight('stock', 'lire') && getDolGlobalString('WAREHOUSE_ASK_WAREHOUSE_DURING_PROJECT') |
||
343 | ), |
||
344 | 'propal' => array( |
||
345 | 'name' => "Proposals", |
||
346 | 'title' => "ListProposalsAssociatedProject", |
||
347 | 'class' => 'Propal', |
||
348 | 'table' => 'propal', |
||
349 | 'datefieldname' => 'datep', |
||
350 | 'urlnew' => constant('BASE_URL') . '/comm/propal/card.php?action=create&origin=project&originid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
351 | 'lang' => 'propal', |
||
352 | 'buttonnew' => 'AddProp', |
||
353 | 'testnew' => $user->hasRight('propal', 'creer'), |
||
354 | 'test' => isModEnabled('propal') && $user->hasRight('propal', 'lire') |
||
355 | ), |
||
356 | 'order' => array( |
||
357 | 'name' => "CustomersOrders", |
||
358 | 'title' => "ListOrdersAssociatedProject", |
||
359 | 'class' => 'Commande', |
||
360 | 'table' => 'commande', |
||
361 | 'datefieldname' => 'date_commande', |
||
362 | 'urlnew' => constant('BASE_URL') . '/commande/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
363 | 'lang' => 'orders', |
||
364 | 'buttonnew' => 'CreateOrder', |
||
365 | 'testnew' => $user->hasRight('commande', 'creer'), |
||
366 | 'test' => isModEnabled('order') && $user->hasRight('commande', 'lire') |
||
367 | ), |
||
368 | 'invoice' => array( |
||
369 | 'name' => "CustomersInvoices", |
||
370 | 'title' => "ListInvoicesAssociatedProject", |
||
371 | 'class' => 'Facture', |
||
372 | 'margin' => 'add', |
||
373 | 'table' => 'facture', |
||
374 | 'datefieldname' => 'datef', |
||
375 | 'urlnew' => constant('BASE_URL') . '/compta/facture/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
376 | 'lang' => 'bills', |
||
377 | 'buttonnew' => 'CreateBill', |
||
378 | 'testnew' => $user->hasRight('facture', 'creer'), |
||
379 | 'test' => isModEnabled('invoice') && $user->hasRight('facture', 'lire') |
||
380 | ), |
||
381 | 'invoice_predefined' => array( |
||
382 | 'name' => "PredefinedInvoices", |
||
383 | 'title' => "ListPredefinedInvoicesAssociatedProject", |
||
384 | 'class' => 'FactureRec', |
||
385 | 'table' => 'facture_rec', |
||
386 | 'datefieldname' => 'datec', |
||
387 | 'urlnew' => constant('BASE_URL') . '/compta/facture/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
388 | 'lang' => 'bills', |
||
389 | 'buttonnew' => 'CreateBill', |
||
390 | 'testnew' => $user->hasRight('facture', 'creer'), |
||
391 | 'test' => isModEnabled('invoice') && $user->hasRight('facture', 'lire') |
||
392 | ), |
||
393 | 'proposal_supplier' => array( |
||
394 | 'name' => "SupplierProposals", |
||
395 | 'title' => "ListSupplierProposalsAssociatedProject", |
||
396 | 'class' => 'SupplierProposal', |
||
397 | 'table' => 'supplier_proposal', |
||
398 | 'datefieldname' => 'date_valid', |
||
399 | 'urlnew' => constant('BASE_URL') . '/supplier_proposal/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), // No socid parameter here, the socid is often the customer and we create a supplier object |
||
400 | 'lang' => 'supplier_proposal', |
||
401 | 'buttonnew' => 'AddSupplierProposal', |
||
402 | 'testnew' => $user->hasRight('supplier_proposal', 'creer'), |
||
403 | 'test' => isModEnabled('supplier_proposal') && $user->hasRight('supplier_proposal', 'lire') |
||
404 | ), |
||
405 | 'order_supplier' => array( |
||
406 | 'name' => "SuppliersOrders", |
||
407 | 'title' => "ListSupplierOrdersAssociatedProject", |
||
408 | 'class' => 'CommandeFournisseur', |
||
409 | 'table' => 'commande_fournisseur', |
||
410 | 'datefieldname' => 'date_commande', |
||
411 | 'urlnew' => constant('BASE_URL') . '/fourn/commande/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), // No socid parameter here, the socid is often the customer and we create a supplier object |
||
412 | 'lang' => 'suppliers', |
||
413 | 'buttonnew' => 'AddSupplierOrder', |
||
414 | 'testnew' => $user->hasRight('fournisseur', 'commande', 'creer') || $user->hasRight('supplier_order', 'creer'), |
||
415 | 'test' => isModEnabled('supplier_order') && $user->hasRight('fournisseur', 'commande', 'lire') || $user->hasRight('supplier_order', 'lire') |
||
416 | ), |
||
417 | 'invoice_supplier' => array( |
||
418 | 'name' => "BillsSuppliers", |
||
419 | 'title' => "ListSupplierInvoicesAssociatedProject", |
||
420 | 'class' => 'FactureFournisseur', |
||
421 | 'margin' => 'minus', |
||
422 | 'table' => 'facture_fourn', |
||
423 | 'datefieldname' => 'datef', |
||
424 | 'urlnew' => constant('BASE_URL') . '/fourn/facture/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), // No socid parameter here, the socid is often the customer and we create a supplier object |
||
425 | 'lang' => 'suppliers', |
||
426 | 'buttonnew' => 'AddSupplierInvoice', |
||
427 | 'testnew' => $user->hasRight('fournisseur', 'facture', 'creer') || $user->hasRight('supplier_invoice', 'creer'), |
||
428 | 'test' => isModEnabled('supplier_invoice') && $user->hasRight('fournisseur', 'facture', 'lire') || $user->hasRight('supplier_invoice', 'lire') |
||
429 | ), |
||
430 | 'contract' => array( |
||
431 | 'name' => "Contracts", |
||
432 | 'title' => "ListContractAssociatedProject", |
||
433 | 'class' => 'Contrat', |
||
434 | 'table' => 'contrat', |
||
435 | 'datefieldname' => 'date_contrat', |
||
436 | 'urlnew' => constant('BASE_URL') . '/contrat/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
437 | 'lang' => 'contracts', |
||
438 | 'buttonnew' => 'AddContract', |
||
439 | 'testnew' => $user->hasRight('contrat', 'creer'), |
||
440 | 'test' => isModEnabled('contract') && $user->hasRight('contrat', 'lire') |
||
441 | ), |
||
442 | 'intervention' => array( |
||
443 | 'name' => "Interventions", |
||
444 | 'title' => "ListFichinterAssociatedProject", |
||
445 | 'class' => 'Fichinter', |
||
446 | 'table' => 'fichinter', |
||
447 | 'datefieldname' => 'date_valid', |
||
448 | 'disableamount' => 0, |
||
449 | 'margin' => '', |
||
450 | 'urlnew' => constant('BASE_URL') . '/fichinter/card.php?action=create&origin=project&originid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
451 | 'lang' => 'interventions', |
||
452 | 'buttonnew' => 'AddIntervention', |
||
453 | 'testnew' => $user->hasRight('ficheinter', 'creer'), |
||
454 | 'test' => isModEnabled('intervention') && $user->hasRight('ficheinter', 'lire') |
||
455 | ), |
||
456 | 'shipping' => array( |
||
457 | 'name' => "Shippings", |
||
458 | 'title' => "ListShippingAssociatedProject", |
||
459 | 'class' => 'Expedition', |
||
460 | 'table' => 'expedition', |
||
461 | 'datefieldname' => 'date_valid', |
||
462 | 'urlnew' => constant('BASE_URL') . '/expedition/card.php?action=create&origin=project&originid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
463 | 'lang' => 'sendings', |
||
464 | 'buttonnew' => 'CreateShipment', |
||
465 | 'testnew' => 0, |
||
466 | 'test' => isModEnabled('shipping') && $user->hasRight('expedition', 'lire') |
||
467 | ), |
||
468 | 'mrp' => array( |
||
469 | 'name' => "MO", |
||
470 | 'title' => "ListMOAssociatedProject", |
||
471 | 'class' => 'Mo', |
||
472 | 'table' => 'mrp_mo', |
||
473 | 'datefieldname' => 'date_valid', |
||
474 | 'urlnew' => constant('BASE_URL') . '/mrp/mo_card.php?action=create&origin=project&originid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
475 | 'lang' => 'mrp', |
||
476 | 'buttonnew' => 'CreateMO', |
||
477 | 'testnew' => $user->hasRight('mrp', 'write'), |
||
478 | 'project_field' => 'fk_project', |
||
479 | 'nototal' => 1, |
||
480 | 'test' => isModEnabled('mrp') && $user->hasRight('mrp', 'read') |
||
481 | ), |
||
482 | 'trip' => array( |
||
483 | 'name' => "TripsAndExpenses", |
||
484 | 'title' => "ListExpenseReportsAssociatedProject", |
||
485 | 'class' => 'Deplacement', |
||
486 | 'table' => 'deplacement', |
||
487 | 'datefieldname' => 'dated', |
||
488 | 'margin' => 'minus', |
||
489 | 'disableamount' => 1, |
||
490 | 'urlnew' => constant('BASE_URL') . '/deplacement/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
491 | 'lang' => 'trips', |
||
492 | 'buttonnew' => 'AddTrip', |
||
493 | 'testnew' => $user->hasRight('deplacement', 'creer'), |
||
494 | 'test' => isModEnabled('deplacement') && $user->hasRight('deplacement', 'lire') |
||
495 | ), |
||
496 | 'expensereport' => array( |
||
497 | 'name' => "ExpenseReports", |
||
498 | 'title' => "ListExpenseReportsAssociatedProject", |
||
499 | 'class' => 'ExpenseReportLine', |
||
500 | 'table' => 'expensereport_det', |
||
501 | 'datefieldname' => 'date', |
||
502 | 'margin' => 'minus', |
||
503 | 'disableamount' => 0, |
||
504 | 'urlnew' => constant('BASE_URL') . '/expensereport/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
505 | 'lang' => 'trips', |
||
506 | 'buttonnew' => 'AddTrip', |
||
507 | 'testnew' => $user->hasRight('expensereport', 'creer'), |
||
508 | 'test' => isModEnabled('expensereport') && $user->hasRight('expensereport', 'lire') |
||
509 | ), |
||
510 | 'donation' => array( |
||
511 | 'name' => "Donation", |
||
512 | 'title' => "ListDonationsAssociatedProject", |
||
513 | 'class' => 'Don', |
||
514 | 'margin' => 'add', |
||
515 | 'table' => 'don', |
||
516 | 'datefieldname' => 'datedon', |
||
517 | 'disableamount' => 0, |
||
518 | 'urlnew' => constant('BASE_URL') . '/don/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
519 | 'lang' => 'donations', |
||
520 | 'buttonnew' => 'AddDonation', |
||
521 | 'testnew' => $user->hasRight('don', 'creer'), |
||
522 | 'test' => isModEnabled('don') && $user->hasRight('don', 'lire') |
||
523 | ), |
||
524 | 'loan' => array( |
||
525 | 'name' => "Loan", |
||
526 | 'title' => "ListLoanAssociatedProject", |
||
527 | 'class' => 'Loan', |
||
528 | 'margin' => 'add', |
||
529 | 'table' => 'loan', |
||
530 | 'datefieldname' => 'datestart', |
||
531 | 'disableamount' => 0, |
||
532 | 'urlnew' => constant('BASE_URL') . '/loan/card.php?action=create&projectid=' . $id . '&socid=' . $socid . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
533 | 'lang' => 'loan', |
||
534 | 'buttonnew' => 'AddLoan', |
||
535 | 'testnew' => $user->hasRight('loan', 'write'), |
||
536 | 'test' => isModEnabled('loan') && $user->hasRight('loan', 'read') |
||
537 | ), |
||
538 | 'chargesociales' => array( |
||
539 | 'name' => "SocialContribution", |
||
540 | 'title' => "ListSocialContributionAssociatedProject", |
||
541 | 'class' => 'ChargeSociales', |
||
542 | 'margin' => 'minus', |
||
543 | 'table' => 'chargesociales', |
||
544 | 'datefieldname' => 'date_ech', |
||
545 | 'disableamount' => 0, |
||
546 | 'urlnew' => constant('BASE_URL') . '/compta/sociales/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
547 | 'lang' => 'compta', |
||
548 | 'buttonnew' => 'AddSocialContribution', |
||
549 | 'testnew' => $user->hasRight('tax', 'charges', 'lire'), |
||
550 | 'test' => isModEnabled('tax') && $user->hasRight('tax', 'charges', 'lire') |
||
551 | ), |
||
552 | 'project_task' => array( |
||
553 | 'name' => "TaskTimeSpent", |
||
554 | 'title' => "ListTaskTimeUserProject", |
||
555 | 'class' => 'Task', |
||
556 | 'margin' => 'minus', |
||
557 | 'table' => 'projet_task', |
||
558 | 'datefieldname' => 'element_date', |
||
559 | 'disableamount' => 0, |
||
560 | 'urlnew' => constant('BASE_URL') . '/projet/tasks/time.php?withproject=1&action=createtime&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
561 | 'buttonnew' => 'AddTimeSpent', |
||
562 | 'testnew' => $user->hasRight('project', 'creer'), |
||
563 | 'test' => isModEnabled('project') && $user->hasRight('projet', 'lire') && !getDolGlobalString('PROJECT_HIDE_TASKS') |
||
564 | ), |
||
565 | 'stock_mouvement' => array( |
||
566 | 'name' => "MouvementStockAssociated", |
||
567 | 'title' => "ListMouvementStockProject", |
||
568 | 'class' => 'StockTransfer', |
||
569 | 'table' => 'stocktransfer_stocktransfer', |
||
570 | 'datefieldname' => 'datem', |
||
571 | 'margin' => 'minus', |
||
572 | 'project_field' => 'fk_project', |
||
573 | 'disableamount' => 0, |
||
574 | 'test' => isModEnabled('stock') && $user->hasRight('stock', 'mouvement', 'lire') && getDolGlobalString('STOCK_MOVEMENT_INTO_PROJECT_OVERVIEW') |
||
575 | ), |
||
576 | 'salaries' => array( |
||
577 | 'name' => "Salaries", |
||
578 | 'title' => "ListSalariesAssociatedProject", |
||
579 | 'class' => 'Salary', |
||
580 | 'table' => 'salary', |
||
581 | 'datefieldname' => 'datesp', |
||
582 | 'margin' => 'minus', |
||
583 | 'disableamount' => 0, |
||
584 | 'urlnew' => constant('BASE_URL') . '/salaries/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
585 | 'lang' => 'salaries', |
||
586 | 'buttonnew' => 'AddSalary', |
||
587 | 'testnew' => $user->hasRight('salaries', 'write'), |
||
588 | 'test' => isModEnabled('salaries') && $user->hasRight('salaries', 'read') |
||
589 | ), |
||
590 | 'variouspayment' => array( |
||
591 | 'name' => "VariousPayments", |
||
592 | 'title' => "ListVariousPaymentsAssociatedProject", |
||
593 | 'class' => 'PaymentVarious', |
||
594 | 'table' => 'payment_various', |
||
595 | 'datefieldname' => 'datev', |
||
596 | 'margin' => 'minus', |
||
597 | 'disableamount' => 0, |
||
598 | 'urlnew' => constant('BASE_URL') . '/compta/bank/various_payment/card.php?action=create&projectid=' . $id . '&backtopage=' . urlencode($_SERVER['PHP_SELF'] . '?id=' . $id), |
||
599 | 'lang' => 'banks', |
||
600 | 'buttonnew' => 'AddVariousPayment', |
||
601 | 'testnew' => $user->hasRight('banque', 'modifier'), |
||
602 | 'test' => isModEnabled("bank") && $user->hasRight('banque', 'lire') && !getDolGlobalString('BANK_USE_OLD_VARIOUS_PAYMENT') |
||
603 | ), |
||
604 | /* No need for this, available on dedicated tab "Agenda/Events" |
||
605 | 'agenda'=>array( |
||
606 | 'name'=>"Agenda", |
||
607 | 'title'=>"ListActionsAssociatedProject", |
||
608 | 'class'=>'ActionComm', |
||
609 | 'table'=>'actioncomm', |
||
610 | 'datefieldname'=>'datep', |
||
611 | 'disableamount'=>1, |
||
612 | 'urlnew'=>DOL_URL_ROOT.'/comm/action/card.php?action=create&projectid='.$id.'&socid='.$socid.'&backtopage='.urlencode($_SERVER['PHP_SELF'].'?id='.$id), |
||
613 | 'lang'=>'agenda', |
||
614 | 'buttonnew'=>'AddEvent', |
||
615 | 'testnew'=>$user->rights->agenda->myactions->create, |
||
616 | 'test'=> isModEnabled('agenda') && $user->hasRight('agenda', 'myactions', 'read')), |
||
617 | */ |
||
618 | ); |
||
619 | |||
620 | // Change rules for profit/benefit calculation |
||
621 | if (getDolGlobalString('PROJECT_ELEMENTS_FOR_PLUS_MARGIN')) { |
||
622 | foreach ($listofreferent as $key => $element) { |
||
623 | if ($listofreferent[$key]['margin'] == 'add') { |
||
624 | unset($listofreferent[$key]['margin']); |
||
625 | } |
||
626 | } |
||
627 | $newelementforplusmargin = explode(',', getDolGlobalString('PROJECT_ELEMENTS_FOR_PLUS_MARGIN')); |
||
628 | foreach ($newelementforplusmargin as $value) { |
||
629 | $listofreferent[trim($value)]['margin'] = 'add'; |
||
630 | } |
||
631 | } |
||
632 | if (getDolGlobalString('PROJECT_ELEMENTS_FOR_MINUS_MARGIN')) { |
||
633 | foreach ($listofreferent as $key => $element) { |
||
634 | if ($listofreferent[$key]['margin'] == 'minus') { |
||
635 | unset($listofreferent[$key]['margin']); |
||
636 | } |
||
637 | } |
||
638 | $newelementforminusmargin = explode(',', getDolGlobalString('PROJECT_ELEMENTS_FOR_MINUS_MARGIN')); |
||
639 | foreach ($newelementforminusmargin as $value) { |
||
640 | $listofreferent[trim($value)]['margin'] = 'minus'; |
||
641 | } |
||
642 | } |
||
643 | |||
644 | |||
645 | $parameters = array('listofreferent' => $listofreferent); |
||
646 | $resHook = $hookmanager->executeHooks('completeListOfReferent', $parameters, $object, $action); |
||
647 | |||
648 | if (!empty($hookmanager->resArray)) { |
||
649 | $listofreferent = array_merge($listofreferent, $hookmanager->resArray); |
||
650 | } |
||
651 | |||
652 | if ($action == "addelement") { |
||
653 | $tablename = GETPOST("tablename"); |
||
654 | $elementselectid = GETPOST("elementselect"); |
||
655 | $result = $object->update_element($tablename, $elementselectid); |
||
656 | if ($result < 0) { |
||
657 | setEventMessages($object->error, $object->errors, 'errors'); |
||
658 | } |
||
659 | } elseif ($action == "unlink") { |
||
660 | $tablename = GETPOST("tablename", "aZ09"); |
||
661 | $projectField = GETPOSTISSET('projectfield') ? GETPOST('projectfield', 'aZ09') : 'fk_projet'; |
||
662 | $elementselectid = GETPOSTINT("elementselect"); |
||
663 | |||
664 | $result = $object->remove_element($tablename, $elementselectid, $projectField); |
||
665 | if ($result < 0) { |
||
666 | setEventMessages($object->error, $object->errors, 'errors'); |
||
667 | } |
||
668 | } |
||
669 | |||
670 | $elementuser = new User($db); |
||
671 | |||
672 | |||
673 | $showdatefilter = 0; |
||
674 | // Show the filter on date on top of element list |
||
675 | if (!$showdatefilter) { |
||
676 | print '<div class="center centpercent">'; |
||
677 | print '<form action="' . $_SERVER["PHP_SELF"] . '?id=' . $object->id . '" method="POST">'; |
||
678 | print '<input type="hidden" name="token" value="' . newToken() . '">'; |
||
679 | print '<input type="hidden" name="tablename" value="' . (empty($tablename) ? '' : $tablename) . '">'; |
||
680 | print '<input type="hidden" name="action" value="view">'; |
||
681 | print '<div class="inline-block">'; |
||
682 | print $form->selectDate($dates, 'dates', 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans("From")); |
||
683 | print '</div>'; |
||
684 | print '<div class="inline-block">'; |
||
685 | print $form->selectDate($datee, 'datee', 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans("to")); |
||
686 | print '</div>'; |
||
687 | print '<div class="inline-block">'; |
||
688 | print '<input type="submit" name="refresh" value="' . $langs->trans("Refresh") . '" class="button small">'; |
||
689 | print '</div>'; |
||
690 | print '</form>'; |
||
691 | print '</div>'; |
||
692 | |||
693 | $showdatefilter++; |
||
694 | } |
||
695 | |||
696 | |||
697 | // Show balance for whole project |
||
698 | |||
699 | $langs->loadLangs(array("suppliers", "bills", "orders", "proposals", "margins")); |
||
700 | |||
701 | if (isModEnabled('stock')) { |
||
702 | $langs->load('stocks'); |
||
703 | } |
||
704 | |||
705 | print load_fiche_titre($langs->trans("Profit"), '', 'title_accountancy'); |
||
706 | |||
707 | print '<table class="noborder centpercent">'; |
||
708 | print '<tr class="liste_titre">'; |
||
709 | print '<td class="left" width="200">'; |
||
710 | $tooltiponprofit = $langs->trans("ProfitIsCalculatedWith") . "<br>\n"; |
||
711 | $tooltiponprofitplus = $tooltiponprofitminus = ''; |
||
712 | foreach ($listofreferent as $key => $value) { |
||
713 | if (!empty($value['lang'])) { |
||
714 | $langs->load($value['lang']); |
||
715 | } |
||
716 | $name = $langs->trans($value['name']); |
||
717 | $qualified = $value['test']; |
||
718 | $margin = empty($value['margin']) ? '' : $value['margin']; |
||
719 | if ($qualified && isset($margin)) { // If this element must be included into profit calculation ($margin is 'minus' or 'add') |
||
720 | if ($margin === 'add') { |
||
721 | $tooltiponprofitplus .= ' > ' . $name . " (+)<br>\n"; |
||
722 | } |
||
723 | if ($margin === 'minus') { |
||
724 | $tooltiponprofitminus .= ' > ' . $name . " (-)<br>\n"; |
||
725 | } |
||
726 | } |
||
727 | } |
||
728 | $tooltiponprofit .= $tooltiponprofitplus; |
||
729 | $tooltiponprofit .= $tooltiponprofitminus; |
||
730 | print $form->textwithpicto($langs->trans("Element"), $tooltiponprofit); |
||
731 | print '</td>'; |
||
732 | print '<td class="right" width="100">' . $langs->trans("Number") . '</td>'; |
||
733 | print '<td class="right" width="100">' . $langs->trans("AmountHT") . '</td>'; |
||
734 | print '<td class="right" width="100">' . $langs->trans("AmountTTC") . '</td>'; |
||
735 | print '</tr>'; |
||
736 | |||
737 | $total_revenue_ht = 0; |
||
738 | $balance_ht = 0; |
||
739 | $balance_ttc = 0; |
||
740 | |||
741 | // Loop on each element type (proposal, sale order, invoices, ...) |
||
742 | foreach ($listofreferent as $key => $value) { |
||
743 | $parameters = array( |
||
744 | 'total_revenue_ht' => & $total_revenue_ht, |
||
745 | 'balance_ht' => & $balance_ht, |
||
746 | 'balance_ttc' => & $balance_ttc, |
||
747 | 'key' => $key, |
||
748 | 'value' => & $value, |
||
749 | 'dates' => $dates, |
||
750 | 'datee' => $datee |
||
751 | ); |
||
752 | $reshook = $hookmanager->executeHooks('printOverviewProfit', $parameters, $object, $action); // Note that $action and $object may have been modified by hook |
||
753 | if ($reshook < 0) { |
||
754 | setEventMessages($hookmanager->error, $hookmanager->errors, 'errors'); |
||
755 | } elseif ($reshook > 0) { |
||
756 | print $hookmanager->resPrint; |
||
757 | continue; |
||
758 | } |
||
759 | |||
760 | $name = $langs->trans($value['name']); |
||
761 | $title = $value['title']; |
||
762 | $classname = $value['class']; |
||
763 | $tablename = $value['table']; |
||
764 | $datefieldname = $value['datefieldname']; |
||
765 | $qualified = $value['test']; |
||
766 | $margin = empty($value['margin']) ? 0 : $value['margin']; |
||
767 | $project_field = empty($value['project_field']) ? '' : $value['project_field']; |
||
768 | if ($qualified && isset($margin)) { // If this element must be included into profit calculation ($margin is 'minus' or 'add') |
||
769 | //$element = new $classname($db); |
||
770 | $element = Misc::getCodeLibClass($classname, $db); |
||
771 | |||
772 | $elementarray = $object->get_element_list($key, $tablename, $datefieldname, $dates, $datee, !empty($project_field) ? $project_field : 'fk_projet'); |
||
773 | |||
774 | if (is_array($elementarray) && count($elementarray) > 0) { |
||
775 | $total_ht = 0; |
||
776 | $total_ttc = 0; |
||
777 | |||
778 | // Loop on each object for the current element type |
||
779 | $num = count($elementarray); |
||
780 | for ($i = 0; $i < $num; $i++) { |
||
781 | $tmp = explode('_', $elementarray[$i]); |
||
782 | $idofelement = $tmp[0]; |
||
783 | $idofelementuser = !empty($tmp[1]) ? $tmp[1] : ""; |
||
784 | |||
785 | $element->fetch($idofelement); |
||
786 | if ($idofelementuser) { |
||
787 | $elementuser->fetch($idofelementuser); |
||
788 | } |
||
789 | |||
790 | // Define if record must be used for total or not |
||
791 | $qualifiedfortotal = true; |
||
792 | if ($key == 'invoice') { |
||
793 | if (!empty($element->close_code) && $element->close_code == 'replaced') { |
||
794 | $qualifiedfortotal = false; // Replacement invoice, do not include into total |
||
795 | } |
||
796 | if (getDolGlobalString('FACTURE_DEPOSITS_ARE_JUST_PAYMENTS') && $element->type == Facture::TYPE_DEPOSIT) { |
||
797 | $qualifiedfortotal = false; // If hidden option to use deposits as payment (deprecated, not recommended to use this), deposits are not included |
||
798 | } |
||
799 | } |
||
800 | if ($key == 'propal') { |
||
801 | if ($element->status != Propal::STATUS_SIGNED && $element->status != Propal::STATUS_BILLED) { |
||
802 | $qualifiedfortotal = false; // Only signed proposal must not be included in total |
||
803 | } |
||
804 | } |
||
805 | |||
806 | if ($tablename != 'expensereport_det' && method_exists($element, 'fetch_thirdparty')) { |
||
807 | $element->fetch_thirdparty(); |
||
808 | } |
||
809 | |||
810 | // Define $total_ht_by_line |
||
811 | if ($tablename == 'don' || $tablename == 'chargesociales' || $tablename == 'payment_various' || $tablename == 'salary') { |
||
812 | $total_ht_by_line = $element->amount; |
||
813 | } elseif ($tablename == 'fichinter') { |
||
814 | $total_ht_by_line = $element->getAmount(); |
||
815 | } elseif ($tablename == 'stock_mouvement') { |
||
816 | $total_ht_by_line = $element->price * abs($element->qty); |
||
817 | } elseif ($tablename == 'projet_task') { |
||
818 | $tmp = $element->getSumOfAmount($idofelementuser ? $elementuser : '', $dates, $datee); |
||
819 | $total_ht_by_line = price2num($tmp['amount'], 'MT'); |
||
820 | } elseif ($key == 'loan') { |
||
821 | if ((empty($dates) && empty($datee)) || (intval($dates) <= $element->datestart && intval($datee) >= $element->dateend)) { |
||
822 | // Get total loan |
||
823 | $total_ht_by_line = -$element->capital; |
||
824 | } else { |
||
825 | // Get loan schedule according to date filter |
||
826 | $total_ht_by_line = 0; |
||
827 | $loanScheduleStatic = new LoanSchedule($element->db); |
||
828 | $loanScheduleStatic->fetchAll($element->id); |
||
829 | if (!empty($loanScheduleStatic->lines)) { |
||
830 | foreach ($loanScheduleStatic->lines as $loanSchedule) { |
||
831 | /** |
||
832 | * @var $loanSchedule LoanSchedule |
||
833 | */ |
||
834 | if ( |
||
835 | ($loanSchedule->datep >= $dates && $loanSchedule->datep <= $datee) // dates filter is defined |
||
836 | || !empty($dates) && empty($datee) && $loanSchedule->datep >= $dates && $loanSchedule->datep <= dol_now() |
||
837 | || empty($dates) && !empty($datee) && $loanSchedule->datep <= $datee |
||
838 | ) { |
||
839 | $total_ht_by_line -= $loanSchedule->amount_capital; |
||
840 | } |
||
841 | } |
||
842 | } |
||
843 | } |
||
844 | } else { |
||
845 | $total_ht_by_line = $element->total_ht; |
||
846 | } |
||
847 | |||
848 | // Define $total_ttc_by_line |
||
849 | if ($tablename == 'don' || $tablename == 'chargesociales' || $tablename == 'payment_various' || $tablename == 'salary') { |
||
850 | $total_ttc_by_line = $element->amount; |
||
851 | } elseif ($tablename == 'fichinter') { |
||
852 | $total_ttc_by_line = $element->getAmount(); |
||
853 | } elseif ($tablename == 'stock_mouvement') { |
||
854 | $total_ttc_by_line = $element->price * abs($element->qty); |
||
855 | } elseif ($tablename == 'projet_task') { |
||
856 | $defaultvat = get_default_tva($mysoc, $mysoc); |
||
857 | $reg = array(); |
||
858 | if (preg_replace('/^(\d+\.)\s\(.*\)/', $defaultvat, $reg)) { |
||
859 | $defaultvat = $reg[1]; |
||
860 | } |
||
861 | $total_ttc_by_line = price2num($total_ht_by_line * (1 + ((float)$defaultvat / 100)), 'MT'); |
||
862 | } elseif ($key == 'loan') { |
||
863 | $total_ttc_by_line = $total_ht_by_line; // For loan there is actually no taxe managed in Dolibarr |
||
864 | } else { |
||
865 | $total_ttc_by_line = $element->total_ttc; |
||
866 | } |
||
867 | |||
868 | // Change sign of $total_ht_by_line and $total_ttc_by_line for some cases |
||
869 | if ($tablename == 'payment_various') { |
||
870 | if ($element->sens == 1) { |
||
871 | $total_ht_by_line = -$total_ht_by_line; |
||
872 | $total_ttc_by_line = -$total_ttc_by_line; |
||
873 | } |
||
874 | } |
||
875 | |||
876 | // Add total if we have to |
||
877 | if ($qualifiedfortotal) { |
||
878 | $total_ht = $total_ht + $total_ht_by_line; |
||
879 | $total_ttc = $total_ttc + $total_ttc_by_line; |
||
880 | } |
||
881 | } |
||
882 | |||
883 | // Each element with at least one line is output |
||
884 | |||
885 | // Calculate margin |
||
886 | if ($margin) { |
||
887 | if ($margin === 'add') { |
||
888 | $total_revenue_ht += $total_ht; |
||
889 | } |
||
890 | |||
891 | if ($margin === "minus") { // Revert sign |
||
892 | $total_ht = -$total_ht; |
||
893 | $total_ttc = -$total_ttc; |
||
894 | } |
||
895 | |||
896 | $balance_ht += $total_ht; |
||
897 | $balance_ttc += $total_ttc; |
||
898 | } |
||
899 | |||
900 | print '<tr class="oddeven">'; |
||
901 | // Module |
||
902 | print '<td class="left">' . $name . '</td>'; |
||
903 | // Nb |
||
904 | print '<td class="right">' . $i . '</td>'; |
||
905 | // Amount HT |
||
906 | print '<td class="right">'; |
||
907 | if ($key == 'intervention' && !$margin) { |
||
908 | print '<span class="opacitymedium">' . $form->textwithpicto($langs->trans("NA"), $langs->trans("AmountOfInteventionNotIncludedByDefault")) . '</span>'; |
||
909 | } else { |
||
910 | if ($key == 'propal') { |
||
911 | print '<span class="opacitymedium">' . $form->textwithpicto('', $langs->trans("SignedOnly")) . '</span>'; |
||
912 | } |
||
913 | print price($total_ht); |
||
914 | } |
||
915 | print '</td>'; |
||
916 | // Amount TTC |
||
917 | print '<td class="right">'; |
||
918 | if ($key == 'intervention' && !$margin) { |
||
919 | print '<span class="opacitymedium">' . $form->textwithpicto($langs->trans("NA"), $langs->trans("AmountOfInteventionNotIncludedByDefault")) . '</span>'; |
||
920 | } else { |
||
921 | if ($key == 'propal') { |
||
922 | print '<span class="opacitymedium">' . $form->textwithpicto('', $langs->trans("SignedOnly")) . '</span>'; |
||
923 | } |
||
924 | print price($total_ttc); |
||
925 | } |
||
926 | print '</td>'; |
||
927 | print '</tr>'; |
||
928 | } |
||
929 | } |
||
930 | } |
||
931 | // and the final balance |
||
932 | print '<tr class="liste_total">'; |
||
933 | print '<td class="right" colspan="2">' . $langs->trans("Profit") . '</td>'; |
||
934 | print '<td class="right">' . price(price2num($balance_ht, 'MT')) . '</td>'; |
||
935 | print '<td class="right">' . price(price2num($balance_ttc, 'MT')) . '</td>'; |
||
936 | print '</tr>'; |
||
937 | |||
938 | // and the cost per attendee |
||
939 | if ($object->usage_organize_event) { |
||
940 | $conforboothattendee = new ConferenceOrBoothAttendee($db); |
||
941 | $result = $conforboothattendee->fetchAll('', '', 0, 0, '(t.fk_project:=:' . ((int)$object->id) . ') AND (t.status:=:' . ConferenceOrBoothAttendee::STATUS_VALIDATED . ')'); |
||
942 | |||
943 | if (!is_array($result) && $result < 0) { |
||
944 | setEventMessages($conforboothattendee->error, $conforboothattendee->errors, 'errors'); |
||
945 | } else { |
||
946 | $nbAttendees = count($result); |
||
947 | } |
||
948 | |||
949 | if ($nbAttendees >= 2) { |
||
950 | $costperattendee_ht = $balance_ht / $nbAttendees; |
||
951 | $costperattendee_ttc = $balance_ttc / $nbAttendees; |
||
952 | print '<tr class="liste_total">'; |
||
953 | print '<td class="right" colspan="2">' . $langs->trans("ProfitPerValidatedAttendee") . '</td>'; |
||
954 | print '<td class="right">' . price(price2num($costperattendee_ht, 'MT')) . '</td>'; |
||
955 | print '<td class="right">' . price(price2num($costperattendee_ttc, 'MT')) . '</td>'; |
||
956 | print '</tr>'; |
||
957 | } |
||
958 | } |
||
959 | |||
960 | // and the margin (profit / revenues) |
||
961 | if ($total_revenue_ht) { |
||
962 | print '<tr class="liste_total">'; |
||
963 | print '<td class="right" colspan="2">' . $langs->trans("Margin") . '</td>'; |
||
964 | print '<td class="right">' . round(100 * $balance_ht / $total_revenue_ht, 1) . '%</td>'; |
||
965 | print '<td class="right"></td>'; |
||
966 | print '</tr>'; |
||
967 | } |
||
968 | |||
969 | print "</table>"; |
||
970 | |||
971 | |||
972 | print '<br><br>'; |
||
973 | print '<br>'; |
||
974 | |||
975 | |||
976 | $total_time = 0; |
||
977 | |||
978 | // Detail |
||
979 | foreach ($listofreferent as $key => $value) { |
||
980 | $parameters = array( |
||
981 | 'key' => $key, |
||
982 | 'value' => & $value, |
||
983 | 'dates' => $dates, |
||
984 | 'datee' => $datee |
||
985 | ); |
||
986 | $reshook = $hookmanager->executeHooks('printOverviewDetail', $parameters, $object, $action); // Note that $action and $object may have been modified by hook |
||
987 | if ($reshook < 0) { |
||
988 | setEventMessages($hookmanager->error, $hookmanager->errors, 'errors'); |
||
989 | } elseif ($reshook > 0) { |
||
990 | print $hookmanager->resPrint; |
||
991 | continue; |
||
992 | } |
||
993 | |||
994 | $title = $value['title']; |
||
995 | $classname = $value['class']; |
||
996 | $tablename = $value['table']; |
||
997 | $datefieldname = $value['datefieldname']; |
||
998 | $qualified = $value['test']; |
||
999 | $urlnew = empty($value['urlnew']) ? '' : $value['urlnew']; |
||
1000 | $buttonnew = empty($value['buttonnew']) ? '' : $value['buttonnew']; |
||
1001 | $testnew = empty($value['testnew']) ? '' : $value['testnew']; |
||
1002 | $project_field = empty($value['project_field']) ? '' : $value['project_field']; |
||
1003 | $nototal = empty($value['nototal']) ? 0 : 1; |
||
1004 | |||
1005 | $exclude_select_element = array('payment_various'); |
||
1006 | if (!empty($value['exclude_select_element'])) { |
||
1007 | $exclude_select_element[] = $value['exclude_select_element']; |
||
1008 | } |
||
1009 | |||
1010 | if ($qualified) { |
||
1011 | // If we want the project task array to have details of users |
||
1012 | //if ($key == 'project_task') $key = 'project_task_time'; |
||
1013 | |||
1014 | //$element = new $classname($db); |
||
1015 | $element = Misc::getCodeLibClass($classname, $db); |
||
1016 | |||
1017 | $addform = ''; |
||
1018 | |||
1019 | $idtofilterthirdparty = 0; |
||
1020 | $array_of_element_linkable_with_different_thirdparty = array('facture_fourn', 'commande_fournisseur'); |
||
1021 | if (!in_array($tablename, $array_of_element_linkable_with_different_thirdparty)) { |
||
1022 | $idtofilterthirdparty = empty($object->thirdparty->id) ? 0 : $object->thirdparty->id; |
||
1023 | if (getDolGlobalString('PROJECT_OTHER_THIRDPARTY_ID_TO_ADD_ELEMENTS')) { |
||
1024 | $idtofilterthirdparty .= ',' . getDolGlobalString('PROJECT_OTHER_THIRDPARTY_ID_TO_ADD_ELEMENTS'); |
||
1025 | } |
||
1026 | } |
||
1027 | |||
1028 | $elementarray = $object->get_element_list($key, $tablename, $datefieldname, $dates, $datee, !empty($project_field) ? $project_field : 'fk_projet'); |
||
1029 | |||
1030 | |||
1031 | if (!getDolGlobalString('PROJECT_LINK_ON_OVERWIEW_DISABLED') && $idtofilterthirdparty && !in_array($tablename, $exclude_select_element)) { |
||
1032 | $selectList = $formproject->select_element($tablename, $idtofilterthirdparty, 'minwidth300 minwidth75imp', -2, empty($project_field) ? 'fk_projet' : $project_field, $langs->trans("SelectElement")); |
||
1033 | if ($selectList < 0) { |
||
1034 | setEventMessages($formproject->error, $formproject->errors, 'errors'); |
||
1035 | } elseif ($selectList) { |
||
1036 | // Define form with the combo list of elements to link |
||
1037 | $addform .= '<div class="inline-block valignmiddle">'; |
||
1038 | $addform .= '<form action="' . $_SERVER["PHP_SELF"] . '?id=' . $object->id . '" method="post">'; |
||
1039 | $addform .= '<input type="hidden" name="token" value="' . newToken() . '">'; |
||
1040 | $addform .= '<input type="hidden" name="tablename" value="' . $tablename . '">'; |
||
1041 | $addform .= '<input type="hidden" name="action" value="addelement">'; |
||
1042 | $addform .= '<input type="hidden" name="datesrfc" value="' . dol_print_date($dates, 'dayhourrfc') . '">'; |
||
1043 | $addform .= '<input type="hidden" name="dateerfc" value="' . dol_print_date($datee, 'dayhourrfc') . '">'; |
||
1044 | $addform .= '<table><tr>'; |
||
1045 | //$addform .= '<td><span class="hideonsmartphone opacitymedium">'.$langs->trans("SelectElement").'</span></td>'; |
||
1046 | $addform .= '<td>' . $selectList . '</td>'; |
||
1047 | $addform .= '<td><input type="submit" class="button button-linkto smallpaddingimp" value="' . dol_escape_htmltag($langs->trans("LinkToElementShort")) . '"></td>'; |
||
1048 | $addform .= '</tr></table>'; |
||
1049 | $addform .= '</form>'; |
||
1050 | $addform .= '</div>'; |
||
1051 | } |
||
1052 | } |
||
1053 | if (!getDolGlobalString('PROJECT_CREATE_ON_OVERVIEW_DISABLED') && $urlnew) { |
||
1054 | $addform .= '<div class="inline-block valignmiddle">'; |
||
1055 | if ($testnew) { |
||
1056 | $addform .= '<a class="buttonxxx marginleftonly" href="' . $urlnew . '" title="' . dol_escape_htmltag($langs->trans($buttonnew)) . '"><span class="fa fa-plus-circle valignmiddle paddingleft"></span></a>'; |
||
1057 | } elseif (!getDolGlobalString('MAIN_BUTTON_HIDE_UNAUTHORIZED')) { |
||
1058 | $addform .= '<span title="' . dol_escape_htmltag($langs->trans($buttonnew)) . '"><a class="buttonxxx marginleftonly buttonRefused" disabled="disabled" href="#"><span class="fa fa-plus-circle valignmiddle paddingleft"></span></a></span>'; |
||
1059 | } |
||
1060 | $addform .= '<div>'; |
||
1061 | } |
||
1062 | |||
1063 | if (is_array($elementarray) && count($elementarray) > 0 && $key == "order_supplier") { |
||
1064 | $addform = '<div class="inline-block valignmiddle"><a id="btnShow" class="buttonxxx marginleftonly" href="#" onClick="return false;"> |
||
1065 | <span id="textBtnShow" class="valignmiddle text-plus-circle hideonsmartphone">' . $langs->trans("CanceledShown") . '</span><span id="minus-circle" class="fa fa-eye valignmiddle paddingleft"></span> |
||
1066 | </a> |
||
1067 | <script> |
||
1068 | $("#btnShow").on("click", function () { |
||
1069 | console.log("We click to show or hide the canceled lines"); |
||
1070 | var attr = $(this).attr("data-canceledarehidden"); |
||
1071 | if (typeof attr !== "undefined" && attr !== false) { |
||
1072 | console.log("Show canceled"); |
||
1073 | $(".tr_canceled").show(); |
||
1074 | $("#textBtnShow").text("' . dol_escape_js($langs->transnoentitiesnoconv("CanceledShown")) . '"); |
||
1075 | $("#btnShow").removeAttr("data-canceledarehidden"); |
||
1076 | $("#minus-circle").removeClass("fa-eye-slash").addClass("fa-eye"); |
||
1077 | } else { |
||
1078 | console.log("Hide canceled"); |
||
1079 | $(".tr_canceled").hide(); |
||
1080 | $("#textBtnShow").text("' . dol_escape_js($langs->transnoentitiesnoconv("CanceledHidden")) . '"); |
||
1081 | $("#btnShow").attr("data-canceledarehidden", 1); |
||
1082 | $("#minus-circle").removeClass("fa-eye").addClass("fa-eye-slash"); |
||
1083 | } |
||
1084 | }); |
||
1085 | </script></div> ' . $addform; |
||
1086 | } |
||
1087 | |||
1088 | print load_fiche_titre($langs->trans($title), $addform, ''); |
||
1089 | |||
1090 | print "\n" . '<!-- Table for tablename = ' . $tablename . ' -->' . "\n"; |
||
1091 | print '<div class="div-table-responsive">'; |
||
1092 | print '<table class="noborder centpercent">'; |
||
1093 | |||
1094 | print '<tr class="liste_titre">'; |
||
1095 | // Remove link column |
||
1096 | print '<td style="width: 24px"></td>'; |
||
1097 | // Ref |
||
1098 | print '<td' . (($tablename != 'actioncomm' && $tablename != 'projet_task') ? ' style="width: 200px"' : '') . '>' . $langs->trans("Ref") . '</td>'; |
||
1099 | // Product and qty on stock_movement |
||
1100 | if ('MouvementStock' == $classname) { |
||
1101 | print '<td style="width: 200px">' . $langs->trans("Product") . '</td>'; |
||
1102 | print '<td style="width: 50px">' . $langs->trans("Qty") . '</td>'; |
||
1103 | } |
||
1104 | // Date |
||
1105 | print '<td' . (($tablename != 'actioncomm' && $tablename != 'projet_task') ? ' style="width: 200px"' : '') . ' class="center">'; |
||
1106 | if (in_array($tablename, array('projet_task'))) { |
||
1107 | print $langs->trans("TimeSpent"); |
||
1108 | } |
||
1109 | if (!in_array($tablename, array('projet_task'))) { |
||
1110 | print $langs->trans("Date"); |
||
1111 | } |
||
1112 | print '</td>'; |
||
1113 | // Thirdparty or user |
||
1114 | print '<td>'; |
||
1115 | if (in_array($tablename, array('projet_task')) && $key == 'project_task') { |
||
1116 | print ''; // if $key == 'project_task', we don't want details per user |
||
1117 | } elseif (in_array($tablename, array('payment_various'))) { |
||
1118 | print ''; // if $key == 'payment_various', we don't have any thirdparty |
||
1119 | } elseif (in_array($tablename, array('expensereport_det', 'don', 'projet_task', 'stock_mouvement', 'salary'))) { |
||
1120 | print $langs->trans("User"); |
||
1121 | } else { |
||
1122 | print $langs->trans("ThirdParty"); |
||
1123 | } |
||
1124 | print '</td>'; |
||
1125 | // Duration of intervention |
||
1126 | if ($tablename == 'fichinter') { |
||
1127 | print '<td>'; |
||
1128 | print $langs->trans("TotalDuration"); |
||
1129 | $total_duration = 0; |
||
1130 | print '</td>'; |
||
1131 | } |
||
1132 | // Amount HT |
||
1133 | //if (empty($value['disableamount']) && ! in_array($tablename, array('projet_task'))) print '<td class="right" width="120">'.$langs->trans("AmountHT").'</td>'; |
||
1134 | //elseif (empty($value['disableamount']) && in_array($tablename, array('projet_task'))) print '<td class="right" width="120">'.$langs->trans("Amount").'</td>'; |
||
1135 | if ($key == 'loan') { |
||
1136 | print '<td class="right" width="120">' . $langs->trans("LoanCapital") . '</td>'; |
||
1137 | } elseif (empty($value['disableamount'])) { |
||
1138 | print '<td class="right" width="120">' . $langs->trans("AmountHT") . '</td>'; |
||
1139 | } else { |
||
1140 | print '<td width="120"></td>'; |
||
1141 | } |
||
1142 | // Amount TTC |
||
1143 | //if (empty($value['disableamount']) && ! in_array($tablename, array('projet_task'))) print '<td class="right" width="120">'.$langs->trans("AmountTTC").'</td>'; |
||
1144 | if ($key == 'loan') { |
||
1145 | print '<td class="right" width="120">' . $langs->trans("RemainderToPay") . '</td>'; |
||
1146 | } elseif (empty($value['disableamount'])) { |
||
1147 | print '<td class="right" width="120">' . $langs->trans("AmountTTC") . '</td>'; |
||
1148 | } else { |
||
1149 | print '<td width="120"></td>'; |
||
1150 | } |
||
1151 | // Status |
||
1152 | if (in_array($tablename, array('projet_task'))) { |
||
1153 | print '<td class="right" width="200">' . $langs->trans("ProgressDeclared") . '</td>'; |
||
1154 | } else { |
||
1155 | print '<td class="right" width="200">' . $langs->trans("Status") . '</td>'; |
||
1156 | } |
||
1157 | print '</tr>'; |
||
1158 | |||
1159 | if (is_array($elementarray) && count($elementarray) > 0) { |
||
1160 | $total_ht = 0; |
||
1161 | $total_ttc = 0; |
||
1162 | |||
1163 | $total_ht_by_third = 0; |
||
1164 | $total_ttc_by_third = 0; |
||
1165 | |||
1166 | $saved_third_id = 0; |
||
1167 | $breakline = ''; |
||
1168 | |||
1169 | if (canApplySubtotalOn($tablename)) { |
||
1170 | // Sort |
||
1171 | $elementarray = sortElementsByClientName($elementarray); |
||
1172 | } |
||
1173 | |||
1174 | $num = count($elementarray); |
||
1175 | for ($i = 0; $i < $num; $i++) { |
||
1176 | $tmp = explode('_', $elementarray[$i]); |
||
1177 | $idofelement = $tmp[0]; |
||
1178 | $idofelementuser = isset($tmp[1]) ? $tmp[1] : ""; |
||
1179 | |||
1180 | $element->fetch($idofelement); |
||
1181 | if ($idofelementuser) { |
||
1182 | $elementuser->fetch($idofelementuser); |
||
1183 | } |
||
1184 | |||
1185 | // Special cases |
||
1186 | if ($tablename != 'expensereport_det') { |
||
1187 | if (method_exists($element, 'fetch_thirdparty')) { |
||
1188 | $element->fetch_thirdparty(); |
||
1189 | } |
||
1190 | } else { |
||
1191 | $expensereport = new ExpenseReport($db); |
||
1192 | $expensereport->fetch($element->fk_expensereport); |
||
1193 | } |
||
1194 | |||
1195 | //print 'xxx'.$tablename.'yyy'.$classname; |
||
1196 | |||
1197 | if ($breakline && $saved_third_id != $element->thirdparty->id) { |
||
1198 | print $breakline; |
||
1199 | |||
1200 | $saved_third_id = $element->thirdparty->id; |
||
1201 | $breakline = ''; |
||
1202 | |||
1203 | $total_ht_by_third = 0; |
||
1204 | $total_ttc_by_third = 0; |
||
1205 | } |
||
1206 | |||
1207 | $saved_third_id = empty($element->thirdparty->id) ? 0 : $element->thirdparty->id; |
||
1208 | |||
1209 | $qualifiedfortotal = true; |
||
1210 | if ($key == 'invoice') { |
||
1211 | if (!empty($element->close_code) && $element->close_code == 'replaced') { |
||
1212 | $qualifiedfortotal = false; // Replacement invoice, do not include into total |
||
1213 | } |
||
1214 | } elseif ($key == 'order_supplier' && $element->status == 7) { |
||
1215 | $qualifiedfortotal = false; // It makes no sense to include canceled orders in the total |
||
1216 | } |
||
1217 | |||
1218 | if ($key == "order_supplier" && $element->status == 7) { |
||
1219 | print '<tr class="oddeven tr_canceled" style=display:none>'; |
||
1220 | } else { |
||
1221 | print '<tr class="oddeven" >'; |
||
1222 | } |
||
1223 | |||
1224 | |||
1225 | // Remove link |
||
1226 | print '<td style="width: 24px">'; |
||
1227 | if ($tablename != 'projet_task' && $tablename != 'stock_mouvement') { |
||
1228 | if (!getDolGlobalString('PROJECT_DISABLE_UNLINK_FROM_OVERVIEW') || $user->admin) { // PROJECT_DISABLE_UNLINK_FROM_OVERVIEW is empty by default, so this test true |
||
1229 | print '<a href="' . $_SERVER["PHP_SELF"] . '?id=' . $object->id . '&action=unlink&tablename=' . $tablename . '&elementselect=' . $element->id . ($project_field ? '&projectfield=' . $project_field : '') . '" class="reposition">'; |
||
1230 | print img_picto($langs->trans('Unlink'), 'unlink'); |
||
1231 | print '</a>'; |
||
1232 | } |
||
1233 | } |
||
1234 | print "</td>\n"; |
||
1235 | |||
1236 | // Ref |
||
1237 | print '<td class="left nowraponall tdoverflowmax250">'; |
||
1238 | if ($tablename == 'expensereport_det') { |
||
1239 | print $expensereport->getNomUrl(1); |
||
1240 | } else { |
||
1241 | // Show ref with link |
||
1242 | if ($element instanceof Task) { |
||
1243 | print $element->getNomUrl(1, 'withproject', 'time'); |
||
1244 | print ' - ' . dol_trunc($element->label, 48); |
||
1245 | } elseif ($key == 'loan') { |
||
1246 | print $element->getNomUrl(1); |
||
1247 | print ' - ' . dol_trunc($element->label, 48); |
||
1248 | } else { |
||
1249 | print $element->getNomUrl(1); |
||
1250 | } |
||
1251 | |||
1252 | $element_doc = $element->element; |
||
1253 | $filename = dol_sanitizeFileName($element->ref); |
||
1254 | if (!empty($conf->$element_doc)) { |
||
1255 | $confelementdoc = $conf->$element_doc; |
||
1256 | $filedir = $confelementdoc->multidir_output[$element->entity] . '/' . dol_sanitizeFileName($element->ref); |
||
1257 | } else { |
||
1258 | $filedir = ''; |
||
1259 | } |
||
1260 | |||
1261 | if ($element_doc === 'order_supplier') { |
||
1262 | $element_doc = 'commande_fournisseur'; |
||
1263 | $filedir = $conf->fournisseur->commande->multidir_output[$element->entity] . '/' . dol_sanitizeFileName($element->ref); |
||
1264 | } elseif ($element_doc === 'invoice_supplier') { |
||
1265 | $element_doc = 'facture_fournisseur'; |
||
1266 | $filename = get_exdir($element->id, 2, 0, 0, $element, 'product') . dol_sanitizeFileName($element->ref); |
||
1267 | $filedir = $conf->fournisseur->facture->multidir_output[$element->entity] . '/' . get_exdir($element->id, 2, 0, 0, $element, 'invoice_supplier') . dol_sanitizeFileName($element->ref); |
||
1268 | } |
||
1269 | |||
1270 | print '<div class="inline-block valignmiddle">'; |
||
1271 | if ($filedir) { |
||
1272 | print $formfile->getDocumentsLink($element_doc, $filename, $filedir); |
||
1273 | } |
||
1274 | print '</div>'; |
||
1275 | |||
1276 | // Show supplier ref |
||
1277 | if (!empty($element->ref_supplier)) { |
||
0 ignored issues
–
show
The property
ref_supplier does not exist on Dolibarr\Code\Projet\Classes\Task . Since you implemented __get , consider adding a @property annotation.
![]() |
|||
1278 | print ' - ' . $element->ref_supplier; |
||
1279 | } |
||
1280 | // Show customer ref |
||
1281 | if (!empty($element->ref_customer)) { |
||
0 ignored issues
–
show
The property
ref_customer does not exist on Dolibarr\Code\Projet\Classes\Task . Since you implemented __get , consider adding a @property annotation.
![]() |
|||
1282 | print ' - ' . $element->ref_customer; |
||
1283 | } |
||
1284 | // Compatibility propale |
||
1285 | if (empty($element->ref_customer) && !empty($element->ref_client)) { |
||
0 ignored issues
–
show
The property
ref_client does not exist on Dolibarr\Code\Projet\Classes\Task . Since you implemented __get , consider adding a @property annotation.
![]() |
|||
1286 | print ' - ' . $element->ref_client; |
||
1287 | } |
||
1288 | } |
||
1289 | print "</td>\n"; |
||
1290 | // Product and qty on stock movement |
||
1291 | if ('MouvementStock' == $classname) { |
||
1292 | $mvsProd = new Product($element->db); |
||
1293 | $mvsProd->fetch($element->product_id); |
||
1294 | print '<td>' . $mvsProd->getNomUrl(1) . '</td>'; |
||
1295 | print '<td>' . $element->qty . '</td>'; |
||
1296 | } |
||
1297 | // Date or TimeSpent |
||
1298 | $date = ''; |
||
1299 | $total_time_by_line = null; |
||
1300 | if ($tablename == 'expensereport_det') { |
||
1301 | $date = $element->date; // No draft status on lines |
||
1302 | } elseif ($tablename == 'stock_mouvement') { |
||
1303 | $date = $element->datem; |
||
1304 | } elseif ($tablename == 'salary') { |
||
1305 | $date = $element->datesp; |
||
1306 | } elseif ($tablename == 'payment_various') { |
||
1307 | $date = $element->datev; |
||
1308 | } elseif ($tablename == 'chargesociales') { |
||
1309 | $date = $element->date_ech; |
||
1310 | } elseif (!empty($element->status) || !empty($element->statut) || !empty($element->fk_status)) { |
||
1311 | if ($tablename == 'don') { |
||
1312 | $date = $element->datedon; |
||
1313 | } |
||
1314 | if ($tablename == 'commande_fournisseur' || $tablename == 'supplier_order') { |
||
1315 | $date = ($element->date_commande ? $element->date_commande : $element->date_valid); |
||
1316 | } elseif ($tablename == 'supplier_proposal') { |
||
1317 | $date = $element->date_validation; // There is no other date for this |
||
1318 | } elseif ($tablename == 'fichinter') { |
||
1319 | $date = $element->datev; // There is no other date for this |
||
1320 | } elseif ($tablename == 'projet_task') { |
||
1321 | $date = ''; // We show no date. Showing date of beginning of task make user think it is date of time consumed |
||
1322 | } else { |
||
1323 | $date = $element->date; // invoice, ... |
||
1324 | if (empty($date)) { |
||
1325 | $date = $element->date_contrat; |
||
1326 | } |
||
1327 | if (empty($date)) { |
||
1328 | $date = $element->datev; |
||
1329 | } |
||
1330 | if (empty($date) && !empty($datefieldname)) { |
||
1331 | $date = $element->$datefieldname; |
||
1332 | } |
||
1333 | } |
||
1334 | } elseif ($key == 'loan') { |
||
1335 | $date = $element->datestart; |
||
1336 | } |
||
1337 | |||
1338 | print '<td class="center">'; |
||
1339 | if ($tablename == 'actioncomm') { |
||
1340 | print dol_print_date($element->datep, 'dayhour'); |
||
1341 | if ($element->datef && $element->datef > $element->datep) { |
||
1342 | print " - " . dol_print_date($element->datef, 'dayhour'); |
||
1343 | } |
||
1344 | } elseif (in_array($tablename, array('projet_task'))) { |
||
1345 | $tmpprojtime = $element->getSumOfAmount($idofelementuser ? $elementuser : '', $dates, $datee); // $element is a task. $elementuser may be empty |
||
1346 | print '<a href="' . constant('BASE_URL') . '/projet/tasks/time.php?id=' . $idofelement . '&withproject=1">'; |
||
1347 | print convertSecondToTime($tmpprojtime['nbseconds'], 'allhourmin'); |
||
1348 | print '</a>'; |
||
1349 | $total_time_by_line = $tmpprojtime['nbseconds']; |
||
1350 | } else { |
||
1351 | print dol_print_date($date, 'day'); |
||
1352 | } |
||
1353 | print '</td>'; |
||
1354 | |||
1355 | // Third party or user |
||
1356 | print '<td class="tdoverflowmax150">'; |
||
1357 | if (is_object($element->thirdparty)) { |
||
1358 | print $element->thirdparty->getNomUrl(1, '', 48); |
||
1359 | } elseif ($tablename == 'expensereport_det') { |
||
1360 | $tmpuser = new User($db); |
||
1361 | $tmpuser->fetch($expensereport->fk_user_author); |
||
1362 | print $tmpuser->getNomUrl(1, '', 48); |
||
1363 | } elseif ($tablename == 'salary') { |
||
1364 | $tmpuser = new User($db); |
||
1365 | $tmpuser->fetch($element->fk_user); |
||
1366 | print $tmpuser->getNomUrl(1, '', 48); |
||
1367 | } elseif ($tablename == 'don' || $tablename == 'stock_mouvement') { |
||
1368 | if ($element->fk_user_author > 0) { |
||
1369 | $tmpuser2 = new User($db); |
||
1370 | $tmpuser2->fetch($element->fk_user_author); |
||
1371 | print $tmpuser2->getNomUrl(1, '', 48); |
||
1372 | } |
||
1373 | } elseif ($tablename == 'projet_task' && $key == 'element_time') { // if $key == 'project_task', we don't want details per user |
||
1374 | print $elementuser->getNomUrl(1); |
||
1375 | } |
||
1376 | print '</td>'; |
||
1377 | |||
1378 | // Add duration and store it in counter for fichinter |
||
1379 | if ($tablename == 'fichinter') { |
||
1380 | print '<td>'; |
||
1381 | print convertSecondToTime($element->duration, 'all', $conf->global->MAIN_DURATION_OF_WORKDAY); |
||
1382 | $total_duration += $element->duration; |
||
1383 | print '</td>'; |
||
1384 | } |
||
1385 | |||
1386 | // Amount without tax |
||
1387 | $warning = ''; |
||
1388 | if (empty($value['disableamount'])) { |
||
1389 | $total_ht_by_line = null; |
||
1390 | $othermessage = ''; |
||
1391 | if ($tablename == 'don' || $tablename == 'chargesociales' || $tablename == 'payment_various' || $tablename == 'salary') { |
||
1392 | $total_ht_by_line = $element->amount; |
||
1393 | } elseif ($tablename == 'fichinter') { |
||
1394 | $total_ht_by_line = $element->getAmount(); |
||
1395 | } elseif ($tablename == 'stock_mouvement') { |
||
1396 | $total_ht_by_line = $element->price * abs($element->qty); |
||
1397 | } elseif (in_array($tablename, array('projet_task'))) { |
||
1398 | if (isModEnabled('salaries')) { |
||
1399 | // TODO Permission to read daily rate to show value |
||
1400 | $total_ht_by_line = price2num($tmpprojtime['amount'], 'MT'); |
||
1401 | if ($tmpprojtime['nblinesnull'] > 0) { |
||
1402 | $langs->load("errors"); |
||
1403 | $warning = $langs->trans("WarningSomeLinesWithNullHourlyRate", $conf->currency); |
||
1404 | } |
||
1405 | } else { |
||
1406 | $othermessage = $form->textwithpicto($langs->trans("NotAvailable"), $langs->trans("ModuleSalaryToDefineHourlyRateMustBeEnabled")); |
||
1407 | } |
||
1408 | } elseif ($key == 'loan') { |
||
1409 | $total_ht_by_line = $element->capital; |
||
1410 | } else { |
||
1411 | $total_ht_by_line = $element->total_ht; |
||
1412 | } |
||
1413 | |||
1414 | // Change sign of $total_ht_by_line and $total_ttc_by_line for some cases |
||
1415 | if ($tablename == 'payment_various') { |
||
1416 | if ($element->sens == 0) { |
||
1417 | $total_ht_by_line = -$total_ht_by_line; |
||
1418 | } |
||
1419 | } |
||
1420 | |||
1421 | print '<td class="right">'; |
||
1422 | if ($othermessage) { |
||
1423 | print $othermessage; |
||
1424 | } |
||
1425 | if (isset($total_ht_by_line)) { |
||
1426 | if (!$qualifiedfortotal) { |
||
1427 | print '<strike>'; |
||
1428 | } |
||
1429 | print '<span class="amount">' . price($total_ht_by_line) . '</span>'; |
||
1430 | if (!$qualifiedfortotal) { |
||
1431 | print '</strike>'; |
||
1432 | } |
||
1433 | } |
||
1434 | if ($warning) { |
||
1435 | print ' ' . img_warning($warning); |
||
1436 | } |
||
1437 | print '</td>'; |
||
1438 | } else { |
||
1439 | print '<td></td>'; |
||
1440 | } |
||
1441 | |||
1442 | // Amount inc tax |
||
1443 | if (empty($value['disableamount'])) { |
||
1444 | $total_ttc_by_line = null; |
||
1445 | if ($tablename == 'don' || $tablename == 'chargesociales' || $tablename == 'payment_various' || $tablename == 'salary') { |
||
1446 | $total_ttc_by_line = $element->amount; |
||
1447 | } elseif ($tablename == 'fichinter') { |
||
1448 | $total_ttc_by_line = $element->getAmount(); |
||
1449 | } elseif ($tablename == 'stock_mouvement') { |
||
1450 | $total_ttc_by_line = $element->price * abs($element->qty); |
||
1451 | } elseif ($tablename == 'projet_task') { |
||
1452 | if (isModEnabled('salaries')) { |
||
1453 | // TODO Permission to read daily rate |
||
1454 | $defaultvat = get_default_tva($mysoc, $mysoc); |
||
1455 | $total_ttc_by_line = price2num($total_ht_by_line * (1 + ($defaultvat / 100)), 'MT'); |
||
1456 | } else { |
||
1457 | $othermessage = $form->textwithpicto($langs->trans("NotAvailable"), $langs->trans("ModuleSalaryToDefineHourlyRateMustBeEnabled")); |
||
1458 | } |
||
1459 | } elseif ($key == 'loan') { |
||
1460 | $total_ttc_by_line = $element->capital - $element->getSumPayment(); |
||
1461 | } else { |
||
1462 | $total_ttc_by_line = $element->total_ttc; |
||
1463 | } |
||
1464 | |||
1465 | // Change sign of $total_ht_by_line and $total_ttc_by_line for some cases |
||
1466 | if ($tablename == 'payment_various') { |
||
1467 | if ($element->sens == 0) { |
||
1468 | $total_ttc_by_line = -$total_ttc_by_line; |
||
1469 | } |
||
1470 | } |
||
1471 | |||
1472 | print '<td class="right">'; |
||
1473 | if ($othermessage) { |
||
1474 | print $othermessage; |
||
1475 | } |
||
1476 | if (isset($total_ttc_by_line)) { |
||
1477 | if (!$qualifiedfortotal) { |
||
1478 | print '<strike>'; |
||
1479 | } |
||
1480 | print '<span class="amount">' . price($total_ttc_by_line) . '</span>'; |
||
1481 | if (!$qualifiedfortotal) { |
||
1482 | print '</strike>'; |
||
1483 | } |
||
1484 | } |
||
1485 | if ($warning) { |
||
1486 | print ' ' . img_warning($warning); |
||
1487 | } |
||
1488 | print '</td>'; |
||
1489 | } else { |
||
1490 | print '<td></td>'; |
||
1491 | } |
||
1492 | |||
1493 | // Status |
||
1494 | print '<td class="right">'; |
||
1495 | if ($tablename == 'expensereport_det') { |
||
1496 | print $expensereport->getLibStatut(5); |
||
1497 | } elseif ($element instanceof CommonInvoice) { |
||
1498 | //This applies for Facture and FactureFournisseur |
||
1499 | print $element->getLibStatut(5, $element->getSommePaiement()); |
||
1500 | } elseif ($element instanceof Task) { |
||
1501 | if ($element->progress != '') { |
||
1502 | print $element->progress . ' %'; |
||
1503 | } |
||
1504 | } elseif ($tablename == 'stock_mouvement') { |
||
1505 | print $element->getLibStatut(3); |
||
1506 | } else { |
||
1507 | print $element->getLibStatut(5); |
||
1508 | } |
||
1509 | print '</td>'; |
||
1510 | |||
1511 | print '</tr>'; |
||
1512 | |||
1513 | if ($qualifiedfortotal) { |
||
1514 | $total_ht = $total_ht + $total_ht_by_line; |
||
1515 | $total_ttc = $total_ttc + $total_ttc_by_line; |
||
1516 | |||
1517 | $total_ht_by_third += $total_ht_by_line; |
||
1518 | $total_ttc_by_third += $total_ttc_by_line; |
||
1519 | |||
1520 | if (!isset($total_time)) { |
||
1521 | $total_time = $total_time_by_line; |
||
1522 | } else { |
||
1523 | $total_time += $total_time_by_line; |
||
1524 | } |
||
1525 | } |
||
1526 | |||
1527 | if (canApplySubtotalOn($tablename)) { |
||
1528 | $breakline = '<tr class="liste_total liste_sub_total">'; |
||
1529 | $breakline .= '<td colspan="2">'; |
||
1530 | $breakline .= '</td>'; |
||
1531 | $breakline .= '<td>'; |
||
1532 | $breakline .= '</td>'; |
||
1533 | $breakline .= '<td class="right">'; |
||
1534 | $breakline .= $langs->trans('SubTotal') . ' : '; |
||
1535 | if (is_object($element->thirdparty)) { |
||
1536 | $breakline .= $element->thirdparty->getNomUrl(0, '', 48); |
||
1537 | } |
||
1538 | $breakline .= '</td>'; |
||
1539 | $breakline .= '<td class="right">' . price($total_ht_by_third) . '</td>'; |
||
1540 | $breakline .= '<td class="right">' . price($total_ttc_by_third) . '</td>'; |
||
1541 | $breakline .= '<td></td>'; |
||
1542 | $breakline .= '</tr>'; |
||
1543 | } |
||
1544 | |||
1545 | //var_dump($element->thirdparty->name.' - '.$saved_third_id.' - '.$element->thirdparty->id); |
||
1546 | } |
||
1547 | |||
1548 | if ($breakline) { |
||
1549 | print $breakline; |
||
1550 | } |
||
1551 | |||
1552 | // Total |
||
1553 | if (empty($nototal)) { |
||
1554 | $colspan = 4; |
||
1555 | if (in_array($tablename, array('projet_task'))) { |
||
1556 | $colspan = 2; |
||
1557 | } |
||
1558 | |||
1559 | print '<tr class="liste_total"><td colspan="' . $colspan . '">' . $langs->trans("Number") . ': ' . $i . '</td>'; |
||
1560 | if (in_array($tablename, array('projet_task'))) { |
||
1561 | print '<td class="center">'; |
||
1562 | print convertSecondToTime($total_time, 'allhourmin'); |
||
1563 | print '</td>'; |
||
1564 | print '<td>'; |
||
1565 | print '</td>'; |
||
1566 | } |
||
1567 | //if (empty($value['disableamount']) && ! in_array($tablename, array('projet_task'))) print '<td class="right" width="100">'.$langs->trans("TotalHT").' : '.price($total_ht).'</td>'; |
||
1568 | //elseif (empty($value['disableamount']) && in_array($tablename, array('projet_task'))) print '<td class="right" width="100">'.$langs->trans("Total").' : '.price($total_ht).'</td>'; |
||
1569 | // If fichinter add the total_duration |
||
1570 | if ($tablename == 'fichinter') { |
||
1571 | print '<td class="left">' . convertSecondToTime($total_duration, 'all', $conf->global->MAIN_DURATION_OF_WORKDAY) . '</td>'; |
||
1572 | } |
||
1573 | print '<td class="right">'; |
||
1574 | if (empty($value['disableamount'])) { |
||
1575 | if ($key == 'loan') { |
||
1576 | print $langs->trans("Total") . ' ' . $langs->trans("LoanCapital") . ' : ' . price($total_ttc); |
||
1577 | } elseif ($tablename != 'projet_task' || isModEnabled('salaries')) { |
||
1578 | print '' . $langs->trans("TotalHT") . ' : ' . price($total_ht); |
||
1579 | } |
||
1580 | } |
||
1581 | print '</td>'; |
||
1582 | //if (empty($value['disableamount']) && ! in_array($tablename, array('projet_task'))) print '<td class="right" width="100">'.$langs->trans("TotalTTC").' : '.price($total_ttc).'</td>'; |
||
1583 | //elseif (empty($value['disableamount']) && in_array($tablename, array('projet_task'))) print '<td class="right" width="100"></td>'; |
||
1584 | print '<td class="right">'; |
||
1585 | if (empty($value['disableamount'])) { |
||
1586 | if ($key == 'loan') { |
||
1587 | print $langs->trans("Total") . ' ' . $langs->trans("RemainderToPay") . ' : ' . price($total_ttc); |
||
1588 | } elseif ($tablename != 'projet_task' || isModEnabled('salaries')) { |
||
1589 | print $langs->trans("TotalTTC") . ' : ' . price($total_ttc); |
||
1590 | } |
||
1591 | } |
||
1592 | print '</td>'; |
||
1593 | print '<td> </td>'; |
||
1594 | print '</tr>'; |
||
1595 | } |
||
1596 | } else { |
||
1597 | if (!is_array($elementarray)) { // error |
||
1598 | print '<tr><td>' . $elementarray . '</td></tr>'; |
||
1599 | } else { |
||
1600 | $colspan = 7; |
||
1601 | if ($tablename == 'fichinter') { |
||
1602 | $colspan++; |
||
1603 | } |
||
1604 | print '<tr><td colspan="' . $colspan . '"><span class="opacitymedium">' . $langs->trans("None") . '</td></tr>'; |
||
1605 | } |
||
1606 | } |
||
1607 | print "</table>"; |
||
1608 | print '</div>'; |
||
1609 | print "<br>\n"; |
||
1610 | } |
||
1611 | } |
||
1612 | |||
1613 | // Enhance with select2 |
||
1614 | if ($conf->use_javascript_ajax) { |
||
1615 | include_once DOL_DOCUMENT_ROOT . '/core/lib/ajax.lib.php'; |
||
1616 | $comboenhancement = ajax_combobox('.elementselect'); |
||
1617 | |||
1618 | print $comboenhancement; |
||
1619 | } |
||
1620 | |||
1621 | // End of page |
||
1622 | ViewMain::llxFooter(); |
||
1623 | $db->close(); |
||
1624 | |||
1625 | |||
1626 | /** |
||
1627 | * Return if we should do a group by customer with sub-total |
||
1628 | * |
||
1629 | * @param string $tablename Name of table |
||
1630 | * @return boolean True to tell to make a group by sub-total |
||
1631 | */ |
||
1632 | function canApplySubtotalOn($tablename) |
||
1633 | { |
||
1634 | global $conf; |
||
1635 | |||
1636 | if (!getDolGlobalString('PROJECT_ADD_SUBTOTAL_LINES')) { |
||
1637 | return false; |
||
1638 | } |
||
1639 | return in_array($tablename, array('facture_fourn', 'commande_fournisseur')); |
||
1640 | } |
||
1641 | |||
1642 | /** |
||
1643 | * sortElementsByClientName |
||
1644 | * |
||
1645 | * @param array $elementarray Element array |
||
1646 | * @return array Element array sorted |
||
1647 | */ |
||
1648 | function sortElementsByClientName($elementarray) |
||
1649 | { |
||
1650 | global $db, $classname; |
||
1651 | |||
1652 | $element = new $classname($db); |
||
1653 | |||
1654 | $clientname = array(); |
||
1655 | foreach ($elementarray as $key => $id) { // id = id of object |
||
1656 | if (empty($clientname[$id])) { |
||
1657 | $element->fetch($id); |
||
1658 | $element->fetch_thirdparty(); |
||
1659 | |||
1660 | $clientname[$id] = $element->thirdparty->name; |
||
1661 | } |
||
1662 | } |
||
1663 | |||
1664 | //var_dump($clientname); |
||
1665 | asort($clientname); // sort on name |
||
1666 | |||
1667 | $elementarray = array(); |
||
1668 | foreach ($clientname as $id => $name) { |
||
1669 | $elementarray[] = $id; |
||
1670 | } |
||
1671 | |||
1672 | return $elementarray; |
||
1673 | } |
||
1674 |
This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.
This is most likely a typographical error or the method has been renamed.