dolibarr 19.0.4
tasks.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2005 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2019 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005-2017 Regis Houssin <regis.houssin@inodbox.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
26require "../main.inc.php";
27require_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
28require_once DOL_DOCUMENT_ROOT.'/projet/class/task.class.php';
29require_once DOL_DOCUMENT_ROOT.'/core/lib/project.lib.php';
30require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
31require_once DOL_DOCUMENT_ROOT.'/core/class/html.formother.class.php';
32require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
33require_once DOL_DOCUMENT_ROOT.'/contact/class/contact.class.php';
34if (isModEnabled('categorie')) {
35 require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php';
36}
37
38// Load translation files required by the page
39$langsLoad=array('projects', 'users', 'companies');
40if (isModEnabled('eventorganization')) {
41 $langsLoad[]='eventorganization';
42}
43
44$langs->loadLangs($langsLoad);
45
46$action = GETPOST('action', 'aZ09');
47$massaction = GETPOST('massaction', 'alpha');
48$show_files = GETPOST('show_files', 'int');
49$confirm = GETPOST('confirm', 'alpha');
50$toselect = GETPOST('toselect', 'array');
51
52$id = GETPOST('id', 'int');
53$ref = GETPOST('ref', 'alpha');
54$taskref = GETPOST('taskref', 'alpha');
55
56// Load variable for pagination
57$limit = GETPOST('limit', 'int') ? GETPOST('limit', 'int') : $conf->liste_limit;
58$sortfield = GETPOST('sortfield', 'aZ09comma');
59$sortorder = GETPOST('sortorder', 'aZ09comma');
60$page = GETPOSTISSET('pageplusone') ? (GETPOST('pageplusone') - 1) : GETPOST("page", 'int');
61if (empty($page) || $page < 0 || GETPOST('button_search', 'alpha') || GETPOST('button_removefilter', 'alpha')) {
62 $page = 0;
63} // If $page is not defined, or '' or -1 or if we click on clear filters
64$offset = $limit * $page;
65$pageprev = $page - 1;
66$pagenext = $page + 1;
67
68$backtopage = GETPOST('backtopage', 'alpha');
69$cancel = GETPOST('cancel', 'alpha');
70
71$search_user_id = GETPOST('search_user_id', 'int');
72$search_taskref = GETPOST('search_taskref');
73$search_tasklabel = GETPOST('search_tasklabel');
74$search_taskdescription = GETPOST('search_taskdescription');
75$search_dtstartday = GETPOST('search_dtstartday');
76$search_dtstartmonth = GETPOST('search_dtstartmonth');
77$search_dtstartyear = GETPOST('search_dtstartyear');
78$search_dtendday = GETPOST('search_dtendday');
79$search_dtendmonth = GETPOST('search_dtendmonth');
80$search_dtendyear = GETPOST('search_dtendyear');
81$search_planedworkload = GETPOST('search_planedworkload');
82$search_timespend = GETPOST('search_timespend');
83$search_progresscalc = GETPOST('search_progresscalc');
84$search_progressdeclare = GETPOST('search_progressdeclare');
85$search_task_budget_amount = GETPOST('search_task_budget_amount');
86
87$search_date_start_startmonth = GETPOST('search_date_start_startmonth', 'int');
88$search_date_start_startyear = GETPOST('search_date_start_startyear', 'int');
89$search_date_start_startday = GETPOST('search_date_start_startday', 'int');
90$search_date_start_start = dol_mktime(0, 0, 0, $search_date_start_startmonth, $search_date_start_startday, $search_date_start_startyear); // Use tzserver
91$search_date_start_endmonth = GETPOST('search_date_start_endmonth', 'int');
92$search_date_start_endyear = GETPOST('search_date_start_endyear', 'int');
93$search_date_start_endday = GETPOST('search_date_start_endday', 'int');
94$search_date_start_end = dol_mktime(23, 59, 59, $search_date_start_endmonth, $search_date_start_endday, $search_date_start_endyear); // Use tzserver
95
96$search_date_end_startmonth = GETPOST('search_date_end_startmonth', 'int');
97$search_date_end_startyear = GETPOST('search_date_end_startyear', 'int');
98$search_date_end_startday = GETPOST('search_date_end_startday', 'int');
99$search_date_end_start = dol_mktime(0, 0, 0, $search_date_end_startmonth, $search_date_end_startday, $search_date_end_startyear); // Use tzserver
100$search_date_end_endmonth = GETPOST('search_date_end_endmonth', 'int');
101$search_date_end_endyear = GETPOST('search_date_end_endyear', 'int');
102$search_date_end_endday = GETPOST('search_date_end_endday', 'int');
103$search_date_end_end = dol_mktime(23, 59, 59, $search_date_end_endmonth, $search_date_end_endday, $search_date_end_endyear); // Use tzserver
104
105$contextpage = GETPOST('contextpage', 'aZ') ? GETPOST('contextpage', 'aZ') : 'projecttasklist';
106$optioncss = GETPOST('optioncss', 'aZ');
107//if (! $user->rights->projet->all->lire) $mine=1; // Special for projects
108
109$object = new Project($db);
110$taskstatic = new Task($db);
111$extrafields = new ExtraFields($db);
112
113include DOL_DOCUMENT_ROOT.'/core/actions_fetchobject.inc.php'; // Must be include, not include_once
114if (getDolGlobalString('PROJECT_ALLOW_COMMENT_ON_PROJECT') && method_exists($object, 'fetchComments') && empty($object->comments)) {
115 $object->fetchComments();
116}
117
118if ($id > 0 || !empty($ref)) {
119 // fetch optionals attributes and labels
120 $extrafields->fetch_name_optionals_label($object->table_element);
121}
122$extrafields->fetch_name_optionals_label($taskstatic->table_element);
123$search_array_options = $extrafields->getOptionalsFromPost($taskstatic->table_element, '', 'search_');
124
125
126// Default sort order (if not yet defined by previous GETPOST)
127/* if (!$sortfield) {
128 reset($object->fields); $sortfield="t.".key($object->fields);
129} // Set here default search field. By default 1st field in definition. Reset is required to avoid key() to return null.
130if (!$sortorder) {
131 $sortorder = "ASC";
132} */
133
134
135// Security check
136$socid = 0;
137//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 assignement.
138$result = restrictedArea($user, 'projet', $id, 'projet&project');
139
140$diroutputmassaction = $conf->project->dir_output.'/tasks/temp/massgeneration/'.$user->id;
141
142// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
143$hookmanager->initHooks(array('projecttaskscard', 'globalcard'));
144
145$progress = GETPOST('progress', 'int');
146$budget_amount = GETPOST('budget_amount', 'int');
147$label = GETPOST('label', 'alpha');
148$description = GETPOST('description', 'restricthtml');
149$planned_workloadhour = (GETPOST('planned_workloadhour', 'int') ? GETPOST('planned_workloadhour', 'int') : 0);
150$planned_workloadmin = (GETPOST('planned_workloadmin', 'int') ? GETPOST('planned_workloadmin', 'int') : 0);
151$planned_workload = $planned_workloadhour * 3600 + $planned_workloadmin * 60;
152
153// Definition of fields for list
154$arrayfields = array(
155 't.ref'=>array('label'=>"RefTask", 'checked'=>1, 'position'=>1),
156 't.label'=>array('label'=>"LabelTask", 'checked'=>1, 'position'=>2),
157 't.description'=>array('label'=>"Description", 'checked'=>0, 'position'=>3),
158 't.dateo'=>array('label'=>"DateStart", 'checked'=>1, 'position'=>4),
159 't.datee'=>array('label'=>"Deadline", 'checked'=>1, 'position'=>5),
160 't.planned_workload'=>array('label'=>"PlannedWorkload", 'checked'=>1, 'position'=>6),
161 't.duration_effective'=>array('label'=>"TimeSpent", 'checked'=>1, 'position'=>7),
162 't.progress_calculated'=>array('label'=>"ProgressCalculated", 'checked'=>1, 'position'=>8),
163 't.progress'=>array('label'=>"ProgressDeclared", 'checked'=>1, 'position'=>9),
164 't.progress_summary'=>array('label'=>"TaskProgressSummary", 'checked'=>1, 'position'=>10),
165 't.budget_amount'=>array('label'=>"Budget", 'checked'=>0, 'position'=>11),
166 'c.assigned'=>array('label'=>"TaskRessourceLinks", 'checked'=>1, 'position'=>12),
167);
168if ($object->usage_bill_time) {
169 $arrayfields['t.tobill'] = array('label'=>$langs->trans("TimeToBill"), 'checked'=>0, 'position'=>11);
170 $arrayfields['t.billed'] = array('label'=>$langs->trans("TimeBilled"), 'checked'=>0, 'position'=>12);
171}
172
173// Extra fields
174$extrafieldsobjectkey = $taskstatic->table_element;
175$extrafieldsobjectprefix = 'efpt.';
176include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_array_fields.tpl.php';
177
178$arrayfields = dol_sort_array($arrayfields, 'position');
179
180$varpage = empty($contextpage) ? $_SERVER["PHP_SELF"] : $contextpage;
181
182
183/*
184 * Actions
185 */
186
187if (GETPOST('cancel', 'alpha')) {
188 $action = 'list';
189 $massaction = '';
190}
191if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
192 $massaction = '';
193}
194
195$parameters = array('id'=>$id);
196$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
197if ($reshook < 0) {
198 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
199}
200
201if (empty($reshook)) {
202 // Selection of new fields
203 include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
204
205 // Purge search criteria
206 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')) { // All tests are required to be compatible with all browsers
207 $search_user_id = "";
208 $search_taskref = '';
209 $search_tasklabel = '';
210 $search_dtstartday = '';
211 $search_dtstartmonth = '';
212 $search_dtstartyear = '';
213 $search_dtendday = '';
214 $search_dtendmonth = '';
215 $search_dtendyear = '';
216 $search_planedworkload = '';
217 $search_timespend = '';
218 $search_progresscalc = '';
219 $search_progressdeclare = '';
220 $search_task_budget_amount = '';
221 $toselect = array();
222 $search_array_options = array();
223 $search_date_start_startmonth = "";
224 $search_date_start_startyear = "";
225 $search_date_start_startday = "";
226 $search_date_start_start = "";
227 $search_date_start_endmonth = "";
228 $search_date_start_endyear = "";
229 $search_date_start_endday = "";
230 $search_date_start_end = "";
231 $search_date_end_startmonth = "";
232 $search_date_end_startyear = "";
233 $search_date_end_startday = "";
234 $search_date_end_start = "";
235 $search_date_end_endmonth = "";
236 $search_date_end_endyear = "";
237 $search_date_end_endday = "";
238 $search_date_end_end = "";
239 }
240
241 // Mass actions
242 $objectclass = 'Task';
243 $objectlabel = 'Tasks';
244 $permissiontoread = $user->hasRight('projet', 'lire');
245 $permissiontodelete = $user->hasRight('projet', 'supprimer');
246 $uploaddir = $conf->project->dir_output.'/tasks';
247 include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';
248}
249
250$morewherefilterarray = array();
251
252if (!empty($search_taskref)) {
253 $morewherefilterarray[] = natural_search('t.ref', $search_taskref, 0, 1);
254}
255
256if (!empty($search_tasklabel)) {
257 $morewherefilterarray[] = natural_search('t.label', $search_tasklabel, 0, 1);
258}
259
260$moresql = dolSqlDateFilter('t.dateo', $search_dtstartday, $search_dtstartmonth, $search_dtstartyear, 1);
261if ($moresql) {
262 $morewherefilterarray[] = $moresql;
263}
264
265$moresql = dolSqlDateFilter('t.datee', $search_dtendday, $search_dtendmonth, $search_dtendyear, 1);
266if ($moresql) {
267 $morewherefilterarray[] = $moresql;
268}
269
270if ($search_date_start_start) {
271 $morewherefilterarray[] = " t.dateo >= '".$db->idate($search_date_start_start)."'";
272}
273if ($search_date_start_end) {
274 $morewherefilterarray[] = " t.dateo <= '".$db->idate($search_date_start_end)."'";
275}
276
277if ($search_date_end_start) {
278 $morewherefilterarray[] = " t.datee >= '".$db->idate($search_date_end_start)."'";
279}
280if ($search_date_end_end) {
281 $morewherefilterarray[] = " t.datee <= '".$db->idate($search_date_end_end)."'";
282}
283
284if (!empty($search_planedworkload)) {
285 $morewherefilterarray[] = natural_search('t.planned_workload', $search_planedworkload, 1, 1);
286}
287
288if (!empty($search_timespend)) {
289 $morewherefilterarray[] = natural_search('t.duration_effective', $search_timespend, 1, 1);
290}
291
292if (!empty($search_progressdeclare)) {
293 $morewherefilterarray[] = natural_search('t.progress', $search_progressdeclare, 1, 1);
294}
295if (!empty($search_progresscalc)) {
296 $morewherefilterarray[] = '(planned_workload IS NULL OR planned_workload = 0 OR '.natural_search('ROUND(100 * duration_effective / planned_workload, 2)', $search_progresscalc, 1, 1).')';
297 //natural_search('round(100 * $line->duration_effective / $line->planned_workload,2)', $filterprogresscalc, 1, 1).' {return 1;} else {return 0;}';
298}
299if ($search_task_budget_amount) {
300 $morewherefilterarray[]= natural_search('t.budget_amount', $search_task_budget_amount, 1, 1);
301}
302//var_dump($morewherefilterarray);
303
304$morewherefilter = '';
305if (count($morewherefilterarray) > 0) {
306 $morewherefilter = ' AND '.implode(' AND ', $morewherefilterarray);
307}
308
309if ($action == 'createtask' && $user->hasRight('projet', 'creer')) {
310 $error = 0;
311
312 // If we use user timezone, we must change also view/list to use user timezone everywhere
313 $date_start = dol_mktime(GETPOST('dateohour', 'int'), GETPOST('dateomin', 'int'), 0, GETPOST('dateomonth', 'int'), GETPOST('dateoday', 'int'), GETPOST('dateoyear', 'int'));
314 $date_end = dol_mktime(GETPOST('dateehour', 'int'), GETPOST('dateemin', 'int'), 0, GETPOST('dateemonth', 'int'), GETPOST('dateeday', 'int'), GETPOST('dateeyear', 'int'));
315
316 if (!$cancel) {
317 if (empty($taskref)) {
318 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentities("Ref")), null, 'errors');
319 $action = 'create';
320 $error++;
321 }
322 if (empty($label)) {
323 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentities("Label")), null, 'errors');
324 $action = 'create';
325 $error++;
326 } elseif (!GETPOST('task_parent')) {
327 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentities("ChildOfProjectTask")), null, 'errors');
328 $action = 'create';
329 $error++;
330 }
331
332 if (!$error) {
333 $tmparray = explode('_', GETPOST('task_parent'));
334 $projectid = $tmparray[0];
335 if (empty($projectid)) {
336 $projectid = $id; // If projectid is ''
337 }
338 $task_parent = $tmparray[1];
339 if (empty($task_parent)) {
340 $task_parent = 0; // If task_parent is ''
341 }
342
343 $task = new Task($db);
344
345 $task->fk_project = $projectid;
346 $task->entity = $object->entity; // Task have the same entity of project
347 $task->ref = $taskref;
348 $task->label = $label;
349 $task->description = $description;
350 $task->planned_workload = $planned_workload;
351 $task->fk_task_parent = $task_parent;
352 $task->date_c = dol_now();
353 $task->date_start = $date_start;
354 $task->date_end = $date_end;
355 $task->progress = $progress;
356 $task->budget_amount = $budget_amount;
357
358 // Fill array 'array_options' with data from add form
359 $ret = $extrafields->setOptionalsFromPost(null, $task);
360
361 $taskid = $task->create($user);
362
363 if ($taskid > 0) {
364 $result = $task->add_contact(GETPOST("userid", 'int'), 'TASKEXECUTIVE', 'internal');
365 } else {
366 if ($db->lasterrno() == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
367 $langs->load("projects");
368 setEventMessages($langs->trans('NewTaskRefSuggested'), null, 'warnings');
369 $duplicate_code_error = true;
370 } else {
371 setEventMessages($task->error, $task->errors, 'errors');
372 }
373 $action = 'create';
374 $error++;
375 }
376 }
377
378 if (!$error) {
379 if (!empty($backtopage)) {
380 header("Location: ".$backtopage);
381 exit;
382 } elseif (empty($projectid)) {
383 header("Location: ".DOL_URL_ROOT.'/projet/tasks/list.php'.(empty($mode) ? '' : '?mode='.$mode));
384 exit;
385 }
386 $id = $projectid;
387 }
388 } else {
389 if (!empty($backtopage)) {
390 header("Location: ".$backtopage);
391 exit;
392 } elseif (empty($id)) {
393 // We go back on task list
394 header("Location: ".DOL_URL_ROOT.'/projet/tasks/list.php'.(empty($mode) ? '' : '?mode='.$mode));
395 exit;
396 }
397 }
398}
399
400
401/*
402 * View
403 */
404
405$now = dol_now();
406$form = new Form($db);
407$formother = new FormOther($db);
408$socstatic = new Societe($db);
409$projectstatic = new Project($db);
410$taskstatic = new Task($db);
411$userstatic = new User($db);
412
413$title = $langs->trans("Tasks").' - '.$object->ref.' '.$object->name;
414if (getDolGlobalString('MAIN_HTML_TITLE') && preg_match('/projectnameonly/', $conf->global->MAIN_HTML_TITLE) && $object->name) {
415 $title = $object->ref.' '.$object->name.' - '.$langs->trans("Tasks");
416}
417if ($action == 'create') {
418 $title = $langs->trans("NewTask");
419}
420$help_url = "EN:Module_Projects|FR:Module_Projets|ES:M&oacute;dulo_Proyectos";
421
422llxHeader("", $title, $help_url);
423
424$arrayofselected = is_array($toselect) ? $toselect : array();
425
426if ($id > 0 || !empty($ref)) {
427 $result = $object->fetch($id, $ref);
428 if ($result < 0) {
429 setEventMessages(null, $object->errors, 'errors');
430 }
431 $result = $object->fetch_thirdparty();
432 if ($result < 0) {
433 setEventMessages(null, $object->errors, 'errors');
434 }
435 $result = $object->fetch_optionals();
436 if ($result < 0) {
437 setEventMessages(null, $object->errors, 'errors');
438 }
439
440
441 // To verify role of users
442 //$userAccess = $object->restrictedProjectArea($user,'read');
443 $userWrite = $object->restrictedProjectArea($user, 'write');
444 //$userDelete = $object->restrictedProjectArea($user,'delete');
445 //print "userAccess=".$userAccess." userWrite=".$userWrite." userDelete=".$userDelete;
446
447
448 $tab = (GETPOSTISSET('tab') ? GETPOST('tab') : 'tasks');
449
450 $head = project_prepare_head($object);
451 print dol_get_fiche_head($head, $tab, $langs->trans("Project"), -1, ($object->public ? 'projectpub' : 'project'));
452
453 $param = '&id='.$object->id;
454 if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
455 $param .= '&contextpage='.urlencode($contextpage);
456 }
457 if ($search_user_id) {
458 $param .= '&search_user_id='.urlencode($search_user_id);
459 }
460 if ($search_taskref) {
461 $param .= '&search_taskref='.urlencode($search_taskref);
462 }
463 if ($search_tasklabel) {
464 $param .= '&search_tasklabel='.urlencode($search_tasklabel);
465 }
466 if ($search_taskdescription) {
467 $param .= '&search_taskdescription='.urlencode($search_taskdescription);
468 }
469 if ($search_dtstartday) {
470 $param .= '&search_dtstartday='.urlencode($search_dtstartday);
471 }
472 if ($search_dtstartmonth) {
473 $param .= '&search_dtstartmonth='.urlencode($search_dtstartmonth);
474 }
475 if ($search_dtstartyear) {
476 $param .= '&search_dtstartyear='.urlencode($search_dtstartyear);
477 }
478 if ($search_dtendday) {
479 $param .= '&search_dtendday='.urlencode($search_dtendday);
480 }
481 if ($search_dtendmonth) {
482 $param .= '&search_dtendmonth='.urlencode($search_dtendmonth);
483 }
484 if ($search_dtendyear) {
485 $param .= '&search_dtendyear='.urlencode($search_dtendyear);
486 }
487 if ($search_date_start_startmonth) {
488 $param .= '&search_date_start_startmonth='.urlencode($search_date_start_startmonth);
489 }
490 if ($search_date_start_startyear) {
491 $param .= '&search_date_start_startyear='.urlencode($search_date_start_startyear);
492 }
493 if ($search_date_start_startday) {
494 $param .= '&search_date_start_startday='.urlencode($search_date_start_startday);
495 }
496 if ($search_date_start_start) {
497 $param .= '&search_date_start_start='.urlencode($search_date_start_start);
498 }
499 if ($search_date_start_endmonth) {
500 $param .= '&search_date_start_endmonth='.urlencode($search_date_start_endmonth);
501 }
502 if ($search_date_start_endyear) {
503 $param .= '&search_date_start_endyear='.urlencode($search_date_start_endyear);
504 }
505 if ($search_date_start_endday) {
506 $param .= '&search_date_start_endday='.urlencode($search_date_start_endday);
507 }
508 if ($search_date_start_end) {
509 $param .= '&search_date_start_end='.urlencode($search_date_start_end);
510 }
511 if ($search_date_end_startmonth) {
512 $param .= '&search_date_end_startmonth='.urlencode($search_date_end_startmonth);
513 }
514 if ($search_date_end_startyear) {
515 $param .= '&search_date_end_startyear='.urlencode($search_date_end_startyear);
516 }
517 if ($search_date_end_startday) {
518 $param .= '&search_date_end_startday='.urlencode($search_date_end_startday);
519 }
520 if ($search_date_end_start) {
521 $param .= '&search_date_end_start='.urlencode($search_date_end_start);
522 }
523 if ($search_date_end_endmonth) {
524 $param .= '&search_date_end_endmonth='.urlencode($search_date_end_endmonth);
525 }
526 if ($search_date_end_endyear) {
527 $param .= '&search_date_end_endyear='.urlencode($search_date_end_endyear);
528 }
529 if ($search_date_end_endday) {
530 $param .= '&search_date_end_endday='.urlencode($search_date_end_endday);
531 }
532 if ($search_date_end_end) {
533 $param .= '&search_date_end_end=' . urlencode($search_date_end_end);
534 }
535 if ($search_planedworkload) {
536 $param .= '&search_planedworkload='.urlencode($search_planedworkload);
537 }
538 if ($search_timespend) {
539 $param .= '&search_timespend='.urlencode($search_timespend);
540 }
541 if ($search_progresscalc) {
542 $param .= '&search_progresscalc='.urlencode($search_progresscalc);
543 }
544 if ($search_progressdeclare) {
545 $param .= '&search_progressdeclare='.urlencode($search_progressdeclare);
546 }
547 if ($search_task_budget_amount) {
548 $param .= '&search_task_budget_amount='.urlencode($search_task_budget_amount);
549 }
550 if ($optioncss != '') {
551 $param .= '&optioncss='.urlencode($optioncss);
552 }
553 // Add $param from extra fields
554 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
555
556 $arrayofmassactions = array();
557 if ($user->hasRight('projet', 'creer')) {
558 $arrayofmassactions['preclonetasks'] = img_picto('', 'clone', 'class="pictofixedwidth"').$langs->trans("Clone");
559 }
560 if ($permissiontodelete) {
561 $arrayofmassactions['predelete'] = img_picto('', 'delete', 'class="pictofixedwidth"').$langs->trans("Delete");
562 }
563 if (in_array($massaction, array('presend', 'predelete'))) {
564 $arrayofmassactions = array();
565 }
566 $massactionbutton = $form->selectMassAction('', $arrayofmassactions);
567
568 // Project card
569
570 if (!empty($_SESSION['pageforbacktolist']) && !empty($_SESSION['pageforbacktolist']['project'])) {
571 $tmpurl = $_SESSION['pageforbacktolist']['project'];
572 $tmpurl = preg_replace('/__SOCID__/', $object->socid, $tmpurl);
573 $linkback = '<a href="'.$tmpurl.(preg_match('/\?/', $tmpurl) ? '&' : '?'). 'restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
574 } else {
575 $linkback = '<a href="'.DOL_URL_ROOT.'/projet/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
576 }
577
578 $morehtmlref = '<div class="refidno">';
579 // Title
580 $morehtmlref .= $object->title;
581 // Thirdparty
582 if (!empty($object->thirdparty->id) && $object->thirdparty->id > 0) {
583 $morehtmlref .= '<br>'.$object->thirdparty->getNomUrl(1, 'project');
584 }
585 $morehtmlref .= '</div>';
586
587 // Define a complementary filter for search of next/prev ref.
588 if (!$user->hasRight('projet', 'all', 'lire')) {
589 $objectsListId = $object->getProjectsAuthorizedForUser($user, 0, 0);
590 $object->next_prev_filter = "rowid IN (".$db->sanitize(count($objectsListId) ? join(',', array_keys($objectsListId)) : '0').")";
591 }
592
593 dol_banner_tab($object, 'ref', $linkback, 1, 'ref', 'ref', $morehtmlref);
594
595 print '<div class="fichecenter">';
596 print '<div class="fichehalfleft">';
597 print '<div class="underbanner clearboth"></div>';
598
599 print '<table class="border tableforfield centpercent">';
600
601 // Usage
602 if (getDolGlobalString('PROJECT_USE_OPPORTUNITIES') || !getDolGlobalString('PROJECT_HIDE_TASKS') || isModEnabled('eventorganization')) {
603 print '<tr><td class="tdtop">';
604 print $langs->trans("Usage");
605 print '</td>';
606 print '<td>';
607 if (getDolGlobalString('PROJECT_USE_OPPORTUNITIES')) {
608 print '<input type="checkbox" disabled name="usage_opportunity"'.(GETPOSTISSET('usage_opportunity') ? (GETPOST('usage_opportunity', 'alpha') != '' ? ' checked="checked"' : '') : ($object->usage_opportunity ? ' checked="checked"' : '')).'"> ';
609 $htmltext = $langs->trans("ProjectFollowOpportunity");
610 print $form->textwithpicto($langs->trans("ProjectFollowOpportunity"), $htmltext);
611 print '<br>';
612 }
613 if (!getDolGlobalString('PROJECT_HIDE_TASKS')) {
614 print '<input type="checkbox" disabled name="usage_task"'.(GETPOSTISSET('usage_task') ? (GETPOST('usage_task', 'alpha') != '' ? ' checked="checked"' : '') : ($object->usage_task ? ' checked="checked"' : '')).'"> ';
615 $htmltext = $langs->trans("ProjectFollowTasks");
616 print $form->textwithpicto($langs->trans("ProjectFollowTasks"), $htmltext);
617 print '<br>';
618 }
619 if (!getDolGlobalString('PROJECT_HIDE_TASKS') && getDolGlobalString('PROJECT_BILL_TIME_SPENT')) {
620 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"' : '')).'"> ';
621 $htmltext = $langs->trans("ProjectBillTimeDescription");
622 print $form->textwithpicto($langs->trans("BillTime"), $htmltext);
623 print '<br>';
624 }
625 if (isModEnabled('eventorganization')) {
626 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"' : '')).'"> ';
627 $htmltext = $langs->trans("EventOrganizationDescriptionLong");
628 print $form->textwithpicto($langs->trans("ManageOrganizeEvent"), $htmltext);
629 }
630 print '</td></tr>';
631 }
632
633 // Visibility
634 print '<tr><td class="titlefield">'.$langs->trans("Visibility").'</td><td>';
635 if ($object->public) {
636 print img_picto($langs->trans('SharedProject'), 'world', 'class="paddingrightonly"');
637 print $langs->trans('SharedProject');
638 } else {
639 print img_picto($langs->trans('PrivateProject'), 'private', 'class="paddingrightonly"');
640 print $langs->trans('PrivateProject');
641 }
642 print '</td></tr>';
643
644 // Budget
645 print '<tr><td>'.$langs->trans("Budget").'</td><td>';
646 if (!is_null($object->budget_amount) && strcmp($object->budget_amount, '')) {
647 print '<span class="amount">'.price($object->budget_amount, '', $langs, 1, 0, 0, $conf->currency).'</span>';
648 }
649 print '</td></tr>';
650
651 // Date start - end project
652 print '<tr><td>'.$langs->trans("Dates").'</td><td>';
653 $start = dol_print_date($object->date_start, 'day');
654 print($start ? $start : '?');
655 $end = dol_print_date($object->date_end, 'day');
656 print ' - ';
657 print($end ? $end : '?');
658 if ($object->hasDelay()) {
659 print img_warning("Late");
660 }
661 print '</td></tr>';
662
663 // Other attributes
664 $cols = 2;
665 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
666
667 print '</table>';
668
669 print '</div>';
670 print '<div class="fichehalfright">';
671 print '<div class="underbanner clearboth"></div>';
672
673 print '<table class="border tableforfield centpercent">';
674
675 // Description
676 print '<td class="titlefield tdtop">'.$langs->trans("Description").'</td><td>';
677 print dol_htmlentitiesbr($object->description);
678 print '</td></tr>';
679
680 // Categories
681 if (isModEnabled('categorie')) {
682 print '<tr><td class="valignmiddle">'.$langs->trans("Categories").'</td><td>';
683 print $form->showCategories($object->id, Categorie::TYPE_PROJECT, 1);
684 print "</td></tr>";
685 }
686
687 print '</table>';
688
689 print '</div>';
690 print '</div>';
691
692 print '<div class="clearboth"></div>';
693
694
695 print dol_get_fiche_end();
696}
697
698
699if ($action == 'create' && $user->hasRight('projet', 'creer') && (empty($object->thirdparty->id) || $userWrite > 0)) {
700 if ($id > 0 || !empty($ref)) {
701 print '<br>';
702 }
703
704 print load_fiche_titre($langs->trans("NewTask"), '', 'projecttask');
705
706 $projectoktoentertime = 1;
707 if ($object->id > 0 && $object->statut == Project::STATUS_CLOSED) {
708 $projectoktoentertime = 0;
709 print '<div class="warning">';
710 $langs->load("errors");
711 print $langs->trans("WarningProjectClosed");
712 print '</div>';
713 }
714
715 if ($object->id > 0 && $object->statut == Project::STATUS_DRAFT) {
716 $projectoktoentertime = 0;
717 print '<div class="warning">';
718 $langs->load("errors");
719 print $langs->trans("WarningProjectDraft");
720 print '</div>';
721 }
722
723 print '<form action="'.$_SERVER['PHP_SELF'].'" method="POST">';
724 print '<input type="hidden" name="token" value="'.newToken().'">';
725 print '<input type="hidden" name="action" value="createtask">';
726 print '<input type="hidden" name="backtopage" value="'.$backtopage.'">';
727 if (!empty($object->id)) {
728 print '<input type="hidden" name="id" value="'.$object->id.'">';
729 }
730
731 print dol_get_fiche_head('');
732
733 print '<div class="div-table-responsive-no-min">';
734 print '<table class="border centpercent">';
735
736 $defaultref = '';
737 $obj = !getDolGlobalString('PROJECT_TASK_ADDON') ? 'mod_task_simple' : $conf->global->PROJECT_TASK_ADDON;
738 if (getDolGlobalString('PROJECT_TASK_ADDON') && is_readable(DOL_DOCUMENT_ROOT."/core/modules/project/task/" . getDolGlobalString('PROJECT_TASK_ADDON').".php")) {
739 require_once DOL_DOCUMENT_ROOT."/core/modules/project/task/" . getDolGlobalString('PROJECT_TASK_ADDON').'.php';
740 $modTask = new $obj();
741 $defaultref = $modTask->getNextValue($object->thirdparty, null);
742 }
743
744 if (is_numeric($defaultref) && $defaultref <= 0) {
745 $defaultref = '';
746 }
747
748 // Ref
749 print '<tr><td class="titlefieldcreate"><span class="fieldrequired">'.$langs->trans("Ref").'</span></td><td>';
750 if (empty($duplicate_code_error)) {
751 print(GETPOSTISSET("ref") ? GETPOST("ref", 'alpha') : $defaultref);
752 } else {
753 print $defaultref;
754 }
755 print '<input type="hidden" name="taskref" value="'.(GETPOSTISSET("ref") ? GETPOST("ref", 'alpha') : $defaultref).'">';
756 print '</td></tr>';
757
758 // Label
759 print '<tr><td class="fieldrequired">'.$langs->trans("Label").'</td><td>';
760 print '<input type="text" name="label" autofocus class="minwidth500" value="'.$label.'">';
761 print '</td></tr>';
762
763 // Project
764 print '<tr><td class="fieldrequired">'.$langs->trans("ChildOfProjectTask").'</td><td>';
765 print img_picto('', 'project', 'class="pictofixedwidth"');
766 if ($projectoktoentertime) {
767 $formother->selectProjectTasks(GETPOST('task_parent'), empty($projectid) ? $object->id : $projectid, 'task_parent', 0, 0, 1, 1, 0, '0,1', 'maxwidth500 widthcentpercentminusxx');
768 } else {
769 $formother->selectProjectTasks(GETPOST('task_parent'), empty($projectid) ? $object->id : $projectid, 'task_parent', 0, 0, 1, 1, 0, '', 'maxwidth500 widthcentpercentminusxx');
770 }
771 print '</td></tr>';
772
773 $contactsofproject = (empty($object->id) ? '' : $object->getListContactId('internal'));
774
775 // Assigned to
776 print '<tr><td>'.$langs->trans("AffectedTo").'</td><td>';
777 print img_picto('', 'user', 'class="pictofixedwidth"');
778 if (is_array($contactsofproject) && count($contactsofproject)) {
779 print $form->select_dolusers($user->id, 'userid', 0, '', 0, '', $contactsofproject, 0, 0, 0, '', 0, '', 'maxwidth500 widthcentpercentminusx');
780 } else {
781 if ((isset($projectid) && $projectid > 0) || $object->id > 0) {
782 print '<span class="opacitymedium">'.$langs->trans("NoUserAssignedToTheProject").'</span>';
783 } else {
784 print $form->select_dolusers($user->id, 'userid', 0, '', 0, '', '', 0, 0, 0, '', 0, '', 'maxwidth500 widthcentpercentminusx');
785 }
786 }
787 print '</td></tr>';
788
789 // Date start task
790 print '<tr><td>'.$langs->trans("DateStart").'</td><td>';
791 print img_picto('', 'action', 'class="pictofixedwidth"');
792 print $form->selectDate((!empty($date_start) ? $date_start : ''), 'dateo', 1, 1, 0, '', 1, 1);
793 print '</td></tr>';
794
795 // Date end task
796 print '<tr><td>'.$langs->trans("DateEnd").'</td><td>';
797 print img_picto('', 'action', 'class="pictofixedwidth"');
798 print $form->selectDate((!empty($date_end) ? $date_end : -1), 'datee', -1, 1, 0, '', 1, 1);
799 print '</td></tr>';
800
801 // Planned workload
802 print '<tr><td>'.$langs->trans("PlannedWorkload").'</td><td>';
803 print img_picto('', 'clock', 'class="pictofixedwidth"');
804 print $form->select_duration('planned_workload', !empty($planned_workload) ? $planned_workload : 0, 0, 'text');
805 print '</td></tr>';
806
807 // Progress
808 print '<tr><td>'.$langs->trans("ProgressDeclared").'</td><td colspan="3">';
809 print img_picto('', 'fa-percent', 'class="pictofixedwidth"');
810 print $formother->select_percent($progress, 'progress', 0, 5, 0, 100, 1);
811 print '</td></tr>';
812
813 // Description
814 print '<tr><td class="tdtop">'.$langs->trans("Description").'</td>';
815 print '<td>';
816
817 // WYSIWYG editor
818 include_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
819 $cked_enabled = (getDolGlobalString('FCKEDITOR_ENABLE_SOCIETE') ? $conf->global->FCKEDITOR_ENABLE_SOCIETE : 0);
820 $nbrows = 0;
821 if (getDolGlobalString('MAIN_INPUT_DESC_HEIGHT')) {
822 $nbrows = $conf->global->MAIN_INPUT_DESC_HEIGHT;
823 }
824 $doleditor = new DolEditor('description', $object->description, '', 80, 'dolibarr_details', '', false, true, $cked_enabled, $nbrows, '90%');
825 print $doleditor->Create();
826
827 print '</td></tr>';
828
829 print '<tr><td>'.$langs->trans("Budget").'</td><td>';
830 print img_picto('', 'currency', 'class="pictofixedwidth"');
831 print '<input size="8" type="text" name="budget_amount" value="'.dol_escape_htmltag(GETPOSTISSET('budget_amount') ? GETPOST('budget_amount') : '').'"></td>';
832 print '</tr>';
833
834 // Other options
835 $parameters = array('arrayfields' => &$arrayfields);
836 $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $taskstatic, $action); // Note that $action and $object may have been modified by hook
837 print $hookmanager->resPrint;
838
839 if (empty($reshook) && !empty($extrafields->attributes[$taskstatic->table_element]['label'])) {
840 print $taskstatic->showOptionals($extrafields, 'edit'); // Do not use $object here that is object of project but use $taskstatic
841 }
842
843 print '</table>';
844 print '</div>';
845
846 print dol_get_fiche_end();
847
848 print $form->buttonsSaveCancel("Add");
849
850 print '</form>';
851} elseif ($id > 0 || !empty($ref)) {
852 $selectedfields = $form->multiSelectArrayWithCheckbox('selectedfields', $arrayfields, $varpage); // This also change content of $arrayfields
853
854 /*
855 * Projet card in view mode
856 */
857
858 print '<br>';
859
860 // Link to create task
861 $linktocreatetaskParam = array();
862 $linktocreatetaskUserRight = false;
863 if ($user->hasRight('projet', 'all', 'creer') || $user->hasRight('projet', 'creer')) {
864 if ($object->public || $userWrite > 0) {
865 $linktocreatetaskUserRight = true;
866 } else {
867 $linktocreatetaskParam['attr']['title'] = $langs->trans("NotOwnerOfProject");
868 }
869 }
870
871 $linktocreatetask = dolGetButtonTitle($langs->trans('AddTask'), '', 'fa fa-plus-circle', DOL_URL_ROOT.'/projet/tasks.php?action=create'.$param.'&backtopage='.urlencode($_SERVER['PHP_SELF'].'?id='.$object->id), '', $linktocreatetaskUserRight, $linktocreatetaskParam);
872
873 print '<form method="POST" id="searchFormList" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'">';
874 print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
875 print '<input type="hidden" name="token" value="'.newToken().'">';
876 print '<input type="hidden" name="action" value="list">';
877 print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
878 print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
879 print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
880 print '<input type="hidden" name="page" value="'.$page.'">';
881 print '<input type="hidden" name="contextpage" value="'.$contextpage.'">';
882
883 $title = $langs->trans("ListOfTasks");
884 $linktotasks = dolGetButtonTitle($langs->trans('ViewList'), '', 'fa fa-bars imgforviewmode', DOL_URL_ROOT.'/projet/tasks.php?id='.$object->id, '', 1, array('morecss'=>'reposition btnTitleSelected'));
885 $linktotasks .= dolGetButtonTitle($langs->trans('ViewGantt'), '', 'fa fa-stream imgforviewmode', DOL_URL_ROOT.'/projet/ganttview.php?id='.$object->id.'&withproject=1', '', 1, array('morecss'=>'reposition marginleftonly'));
886
887 //print_barre_liste($title, 0, $_SERVER["PHP_SELF"], '', $sortfield, $sortorder, $linktotasks, $num, $totalnboflines, 'generic', 0, '', '', 0, 1);
888 print load_fiche_titre($title, $linktotasks.' &nbsp; '.$linktocreatetask, 'projecttask', '', '', '', $massactionbutton);
889
890 $objecttmp = new Task($db);
891 $trackid = 'task'.$taskstatic->id;
892 include DOL_DOCUMENT_ROOT.'/core/tpl/massactions_pre.tpl.php';
893
894 // Get list of tasks in tasksarray and taskarrayfiltered
895 // We need all tasks (even not limited to a user because a task to user can have a parent that is not affected to him).
896 $filteronthirdpartyid = $socid;
897 $tasksarray = $taskstatic->getTasksArray(0, 0, $object->id, $filteronthirdpartyid, 0, '', -1, $morewherefilter, 0, 0, $extrafields, 1, $search_array_options, 1, 1, $sortfield, $sortorder);
898
899 // We load also tasks limited to a particular user
900 $tmpuser = new User($db);
901 if ($search_user_id > 0) {
902 $tmpuser->fetch($search_user_id);
903 }
904
905 $tasksrole = ($tmpuser->id > 0 ? $taskstatic->getUserRolesForProjectsOrTasks(null, $tmpuser, $object->id, 0) : '');
906 //var_dump($tasksarray);
907 //var_dump($tasksrole);
908
909 if (!empty($conf->use_javascript_ajax)) {
910 include DOL_DOCUMENT_ROOT.'/core/tpl/ajaxrow.tpl.php';
911 }
912
913 // Filter on assigned users
914 $moreforfilter = '';
915 $moreforfilter .= '<div class="divsearchfield">';
916 $moreforfilter .= img_picto('', 'user', 'class="pictofixedwidth"');
917 $moreforfilter .= $form->select_dolusers($tmpuser->id > 0 ? $tmpuser->id : '', 'search_user_id', $langs->trans("TasksAssignedTo"), null, 0, '', '');
918 $moreforfilter .= '</div>';
919 if ($moreforfilter) {
920 print '<div class="liste_titre liste_titre_bydiv centpercent">';
921 print $moreforfilter;
922 print '</div>';
923 }
924
925 // Show the massaction checkboxes only when this page is not opend from the Extended POS
926 if ($massactionbutton && $contextpage != 'poslist') {
927 $selectedfields.= $form->showCheckAddButtons('checkforselect', 1);
928 }
929
930 print '<div class="div-table-responsive">';
931 print '<table id="tablelines" class="tagtable nobottom liste'.($moreforfilter ? " listwithfilterbefore" : "").'">';
932
933 // Fields title search
934 print '<tr class="liste_titre_filter">';
935
936 // Action column
937 if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
938 print '<td class="liste_titre maxwidthsearch">';
939 $searchpicto = $form->showFilterButtons();
940 print $searchpicto;
941 print '</td>';
942 }
943
944 if (!empty($arrayfields['t.ref']['checked'])) {
945 print '<td class="liste_titre">';
946 print '<input class="flat searchstring maxwidth50" type="text" name="search_taskref" value="'.dol_escape_htmltag($search_taskref).'">';
947 print '</td>';
948 }
949
950 if (!empty($arrayfields['t.label']['checked'])) {
951 print '<td class="liste_titre">';
952 print '<input class="flat searchstring maxwidth100" type="text" name="search_tasklabel" value="'.dol_escape_htmltag($search_tasklabel).'">';
953 print '</td>';
954 }
955
956 if (!empty($arrayfields['t.description']['checked'])) {
957 print '<td class="liste_titre">';
958 print '<input class="flat searchstring maxwidth100" type="text" name="search_taskdescription" value="'.dol_escape_htmltag($search_taskdescription).'">';
959 print '</td>';
960 }
961
962 if (!empty($arrayfields['t.dateo']['checked'])) {
963 print '<td class="liste_titre center">';
964 /*print '<span class="nowraponall"><input class="flat valignmiddle width20" type="text" maxlength="2" name="search_dtstartday" value="'.$search_dtstartday.'">';
965 print '<input class="flat valignmiddle width20" type="text" maxlength="2" name="search_dtstartmonth" value="'.$search_dtstartmonth.'"></span>';
966 print $formother->selectyear($search_dtstartyear ? $search_dtstartyear : -1, 'search_dtstartyear', 1, 20, 5);*/
967 print '<div class="nowrapfordate">';
968 print $form->selectDate($search_date_start_start ? $search_date_start_start : -1, 'search_date_start_start', 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('From'));
969 print '</div>';
970 print '<div class="nowrapfordate">';
971 print $form->selectDate($search_date_start_end ? $search_date_start_end : -1, 'search_date_start_end', 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('to'));
972 print '</div>';
973 print '</td>';
974 }
975
976 if (!empty($arrayfields['t.datee']['checked'])) {
977 print '<td class="liste_titre center">';
978 /*print '<span class="nowraponall"><input class="flat valignmiddle width20" type="text" maxlength="2" name="search_dtendday" value="'.$search_dtendday.'">';
979 print '<input class="flat valignmiddle width20" type="text" maxlength="2" name="search_dtendmonth" value="'.$search_dtendmonth.'"></span>';
980 print $formother->selectyear($search_dtendyear ? $search_dtendyear : -1, 'search_dtendyear', 1, 20, 5);*/
981 print '<div class="nowrapfordate">';
982 print $form->selectDate($search_date_end_start ? $search_date_end_start : -1, 'search_date_end_start', 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('From'));
983 print '</div>';
984 print '<div class="nowrapfordate">';
985 print $form->selectDate($search_date_end_end ? $search_date_end_end : -1, 'search_date_end_end', 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('to'));
986 print '</div>';
987 print '</td>';
988 }
989
990 if (!empty($arrayfields['t.planned_workload']['checked'])) {
991 print '<td class="liste_titre right">';
992 print '<input class="flat" type="text" size="4" name="search_planedworkload" value="'.$search_planedworkload.'">';
993 print '</td>';
994 }
995
996 if (!empty($arrayfields['t.duration_effective']['checked'])) {
997 print '<td class="liste_titre right">';
998 print '<input class="flat" type="text" size="4" name="search_timespend" value="'.$search_timespend.'">';
999 print '</td>';
1000 }
1001
1002 if (!empty($arrayfields['t.progress_calculated']['checked'])) {
1003 print '<td class="liste_titre right">';
1004 print '<input class="flat" type="text" size="4" name="search_progresscalc" value="'.$search_progresscalc.'">';
1005 print '</td>';
1006 }
1007
1008 if (!empty($arrayfields['t.progress']['checked'])) {
1009 print '<td class="liste_titre right">';
1010 print '<input class="flat" type="text" size="4" name="search_progressdeclare" value="'.$search_progressdeclare.'">';
1011 print '</td>';
1012 }
1013
1014 // progress resume not searchable
1015 if (!empty($arrayfields['t.progress_summary']['checked'])) {
1016 print '<td class="liste_titre right"></td>';
1017 }
1018
1019 if ($object->usage_bill_time) {
1020 if (!empty($arrayfields['t.tobill']['checked'])) {
1021 print '<td class="liste_titre right">';
1022 print '</td>';
1023 }
1024
1025 if (!empty($arrayfields['t.billed']['checked'])) {
1026 print '<td class="liste_titre right">';
1027 print '</td>';
1028 }
1029 }
1030 // Contacts of task, disabled because available by default jsut after
1031 /*
1032 if (!empty($conf->global->PROJECT_SHOW_CONTACTS_IN_LIST)) {
1033 print '<td class="liste_titre"></td>';
1034 }
1035 */
1036
1037 if (!empty($arrayfields['t.budget_amount']['checked'])) {
1038 print '<td class="liste_titre center">';
1039 print '<input type="text" class="flat" name="search_task_budget_amount" value="'.$search_task_budget_amount.'" size="4">';
1040 print '</td>';
1041 }
1042
1043 if (!empty($arrayfields['c.assigned']['checked'])) {
1044 print '<td class="liste_titre right">';
1045 print '</td>';
1046 }
1047
1048 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_input.tpl.php';
1049
1050 print '<td class="liste_titre maxwidthsearch">&nbsp;</td>';
1051
1052 // Action column
1053 if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1054 print '<td class="liste_titre maxwidthsearch">';
1055 $searchpicto = $form->showFilterButtons();
1056 print $searchpicto;
1057 print '</td>';
1058 }
1059
1060 print "</tr>\n";
1061
1062 print '<tr class="liste_titre nodrag nodrop">';
1063 // Action column
1064 if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1065 print_liste_field_titre($selectedfields, $_SERVER["PHP_SELF"], "", '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ');
1066 }
1067 // print '<td>'.$langs->trans("Project").'</td>';
1068 if (!empty($arrayfields['t.ref']['checked'])) {
1069 print_liste_field_titre($arrayfields['t.ref']['label'], $_SERVER["PHP_SELF"], 't.ref', '', $param, '', $sortfield, $sortorder, '');
1070 }
1071 if (!empty($arrayfields['t.label']['checked'])) {
1072 print_liste_field_titre($arrayfields['t.label']['label'], $_SERVER["PHP_SELF"], "t.label", '', $param, '', $sortfield, $sortorder, '');
1073 }
1074 if (!empty($arrayfields['t.description']['checked'])) {
1075 print_liste_field_titre($arrayfields['t.description']['label'], $_SERVER["PHP_SELF"], "", '', $param, '', $sortfield, $sortorder, '');
1076 }
1077 if (!empty($arrayfields['t.dateo']['checked'])) {
1078 print_liste_field_titre($arrayfields['t.dateo']['label'], $_SERVER["PHP_SELF"], "t.dateo", '', $param, '', $sortfield, $sortorder, 'center ');
1079 }
1080 if (!empty($arrayfields['t.datee']['checked'])) {
1081 print_liste_field_titre($arrayfields['t.datee']['label'], $_SERVER["PHP_SELF"], "t.datee", '', $param, '', $sortfield, $sortorder, 'center ');
1082 }
1083 if (!empty($arrayfields['t.planned_workload']['checked'])) {
1084 print_liste_field_titre($arrayfields['t.planned_workload']['label'], $_SERVER["PHP_SELF"], "t.planned_workload", '', $param, '', $sortfield, $sortorder, 'right ', '', 1);
1085 }
1086 if (!empty($arrayfields['t.duration_effective']['checked'])) {
1087 print_liste_field_titre($arrayfields['t.duration_effective']['label'], $_SERVER["PHP_SELF"], "t.duration_effective", '', $param, '', $sortfield, $sortorder, 'right ', '', 1);
1088 }
1089 if (!empty($arrayfields['t.progress_calculated']['checked'])) {
1090 print_liste_field_titre($arrayfields['t.progress_calculated']['label'], $_SERVER["PHP_SELF"], "", '', $param, '', $sortfield, $sortorder, 'right ', '', 1);
1091 }
1092 if (!empty($arrayfields['t.progress']['checked'])) {
1093 print_liste_field_titre($arrayfields['t.progress']['label'], $_SERVER["PHP_SELF"], "t.progress", '', $param, '', $sortfield, $sortorder, 'right ', '', 1);
1094 }
1095 if (!empty($arrayfields['t.progress_summary']['checked'])) {
1096 print_liste_field_titre($arrayfields['t.progress_summary']['label'], $_SERVER["PHP_SELF"], "", '', $param, '', $sortfield, $sortorder, 'center ', '', 1);
1097 }
1098 if ($object->usage_bill_time) {
1099 if (!empty($arrayfields['t.tobill']['checked'])) {
1100 print_liste_field_titre($arrayfields['t.tobill']['label'], $_SERVER["PHP_SELF"], "t.tobill", '', $param, '', $sortfield, $sortorder, 'right ');
1101 }
1102 if (!empty($arrayfields['t.billed']['checked'])) {
1103 print_liste_field_titre($arrayfields['t.billed']['label'], $_SERVER["PHP_SELF"], "t.billed", '', $param, '', $sortfield, $sortorder, 'right ');
1104 }
1105 }
1106 // Contacts of task, disabled because available by default jsut after
1107 /*
1108 if (!empty($conf->global->PROJECT_SHOW_CONTACTS_IN_LIST)) {
1109 print_liste_field_titre("TaskRessourceLinks", $_SERVER["PHP_SELF"], '', '', $param, $sortfield, $sortorder);
1110 }
1111 */
1112
1113 if (!empty($arrayfields['t.budget_amount']['checked'])) {
1114 print_liste_field_titre($arrayfields['t.budget_amount']['label'], $_SERVER["PHP_SELF"], "t.budget_amount", "", $param, '', $sortfield, $sortorder, 'center ');
1115 }
1116
1117 if (!empty($arrayfields['c.assigned']['checked'])) {
1118 print_liste_field_titre($arrayfields['c.assigned']['label'], $_SERVER["PHP_SELF"], "", '', $param, '', $sortfield, $sortorder, 'center ', '');
1119 }
1120 // Extra fields
1121 $disablesortlink = 1;
1122 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_title.tpl.php';
1123 // Hook fields
1124 $parameters = array('arrayfields'=>$arrayfields, 'param'=>$param, 'sortfield'=>$sortfield, 'sortorder'=>$sortorder);
1125 $reshook = $hookmanager->executeHooks('printFieldListTitle', $parameters); // Note that $action and $object may have been modified by hook
1126 print $hookmanager->resPrint;
1127 print '<td></td>';
1128 // Action column
1129 if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
1130 print_liste_field_titre($selectedfields, $_SERVER["PHP_SELF"], "", '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ');
1131 }
1132 print "</tr>\n";
1133
1134 $nboftaskshown = 0;
1135 if (count($tasksarray) > 0) {
1136 // Show all lines in taskarray (recursive function to go down on tree)
1137 $j = 0;
1138 $level = 0;
1139 $nboftaskshown = projectLinesa($j, 0, $tasksarray, $level, true, 0, $tasksrole, $object->id, 1, $object->id, '', ($object->usage_bill_time ? 1 : 0), $arrayfields, $arrayofselected);
1140 } else {
1141 $colspan = count($arrayfields);
1142 if ($object->usage_bill_time) {
1143 $colspan += 2;
1144 }
1145 print '<tr class="oddeven"><td colspan="'.$colspan.'"><span class="opacitymedium">'.$langs->trans("NoTasks").'</span></td></tr>';
1146 }
1147
1148 print "</table>";
1149 print '</div>';
1150
1151 print '</form>';
1152
1153
1154 // Test if database is clean. If not we clean it.
1155 //print 'mode='.$_REQUEST["mode"].' $nboftaskshown='.$nboftaskshown.' count($tasksarray)='.count($tasksarray).' count($tasksrole)='.count($tasksrole).'<br>';
1156 if ($user->hasRight('projet', 'all', 'lire')) { // We make test to clean only if user has permission to see all (test may report false positive otherwise)
1157 if ($search_user_id == $user->id) {
1158 if ($nboftaskshown < count($tasksrole)) {
1159 include_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
1160 cleanCorruptedTree($db, 'projet_task', 'fk_task_parent');
1161 }
1162 } else {
1163 if ($nboftaskshown < count($tasksarray) && !GETPOST('search_user_id', 'int')) {
1164 include_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
1165 cleanCorruptedTree($db, 'projet_task', 'fk_task_parent');
1166 }
1167 }
1168 }
1169}
1170
1171// End of page
1172llxFooter();
1173$db->close();
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader()
Empty header.
Definition wrapper.php:55
llxFooter()
Empty footer.
Definition wrapper.php:69
Class to manage a WYSIWYG editor.
Class to manage standard extra fields.
Class to manage generation of HTML components Only common components must be here.
Classe permettant la generation de composants html autre Only common components are here.
Class to manage projects.
const STATUS_CLOSED
Closed status.
const STATUS_DRAFT
Draft status.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage tasks.
Class to manage Dolibarr users.
dolSqlDateFilter($datefield, $day_date, $month_date, $year_date, $excludefirstand=0, $gm=false)
Generate a SQL string to make a filter into a range (for second of date until last second of date).
Definition date.lib.php:377
cleanCorruptedTree($db, $tabletocleantree, $fieldfkparent)
Clean corrupted tree (orphelins linked to a not existing parent), record linked to themself and child...
dol_banner_tab($object, $paramid, $morehtml='', $shownav=1, $fieldid='rowid', $fieldref='ref', $morehtmlref='', $moreparam='', $nodbprefix=0, $morehtmlleft='', $morehtmlstatus='', $onlybanner=0, $morehtmlright='')
Show tab footer of a card.
dol_mktime($hour, $minute, $second, $month, $day, $year, $gm='auto', $check=1)
Return a timestamp date built from detailed informations (by default a local PHP server timestamp) Re...
load_fiche_titre($titre, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='')
Load a title with picto.
img_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='', $dragdropfile=0)
Show tabs of a record.
dolGetButtonTitle($label, $helpText='', $iconClass='fa fa-file', $url='', $id='', $status=1, $params=array())
Function dolGetButtonTitle : this kind of buttons are used in title in list.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
natural_search($fields, $value, $mode=0, $nofirstand=0)
Generate natural SQL search string for a criteria (this criteria can be tested on one or several fiel...
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs='', $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
dol_now($mode='auto')
Return date for now.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
dol_sort_array(&$array, $index, $order='asc', $natsort=0, $case_sensitive=0, $keepindex=0)
Advanced sort array by second index function, which produces ascending (default) or descending output...
print_liste_field_titre($name, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $tooltip="", $forcenowrapcolumntitle=0)
Show title line of an array.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0)
Set event messages in dol_events session object.
dol_htmlentitiesbr($stringtoencode, $nl2brmode=0, $pagecodefrom='UTF-8', $removelasteolbr=1)
This function is called to encode a string into a HTML string but differs from htmlentities because a...
getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
projectLinesa(&$inc, $parent, &$lines, &$level, $var, $showproject, &$taskrole, $projectsListId='', $addordertick=0, $projectidfortotallink=0, $dummy='', $showbilltime=0, $arrayfields=array(), $arrayofselected=array())
Show task lines with a particular parent.
project_prepare_head(Project $project, $moreparam='')
Prepare array with list of tabs.
restrictedArea(User $user, $features, $object=0, $tableandshare='', $feature2='', $dbt_keyfield='fk_soc', $dbt_select='rowid', $isdraft=0, $mode=0)
Check permissions of a user to show a page and an object.