diff --git a/app/Http/Requests/UpdateUserRequest.php b/app/Http/Requests/UpdateUserRequest.php
index bc97f78cc..d95cba607 100644
--- a/app/Http/Requests/UpdateUserRequest.php
+++ b/app/Http/Requests/UpdateUserRequest.php
@@ -34,9 +34,10 @@ public function rules()
{
$id = $this->route('user')->id;
$rules = [
- 'name' => 'required|unique:users,name,'.$id,
- 'email' => 'required|email|unique:users,email,'.$id.'|regex:/^[\w\-\.\+]+\@[a-zA-Z0-9\.\-]+\.[a-zA-z0-9]{2,4}$/',
- 'phone' => 'nullable|numeric|digits:10',
+ 'name' => 'required|unique:users,name,'.$id,
+ 'email' => 'required|email|unique:users,email,'.$id.'|regex:/^[\w\-\.\+]+\@[a-zA-Z0-9\.\-]+\.[a-zA-z0-9]{2,4}$/',
+ 'phone' => 'nullable|numeric|digits:10',
+ 'role_id' => 'required',
];
return $rules;
diff --git a/app/Models/User.php b/app/Models/User.php
index db381f64d..84bde1672 100644
--- a/app/Models/User.php
+++ b/app/Models/User.php
@@ -112,15 +112,17 @@ class User extends Authenticatable
* @var array
*/
public static $rules = [
- 'name' => 'required|unique:users,name',
- 'email' => 'required|email|unique:users,email|regex:/^[\w\-\.\+]+\@[a-zA-Z0-9\.\-]+\.[a-zA-z0-9]{2,4}$/',
- 'phone' => 'nullable|numeric|digits:10',
+ 'name' => 'required|unique:users,name',
+ 'email' => 'required|email|unique:users,email|regex:/^[\w\-\.\+]+\@[a-zA-Z0-9\.\-]+\.[a-zA-z0-9]{2,4}$/',
+ 'phone' => 'nullable|numeric|digits:10',
+ 'role_id' => 'required',
];
public static $messages = [
- 'phone.digits' => 'The phone number must be 10 digits long.',
- 'email.regex' => 'Please enter valid email.',
- 'photo.mimes' => 'The profile image must be a file of type: jpeg, jpg, png.',
+ 'phone.digits' => 'The phone number must be 10 digits long.',
+ 'email.regex' => 'Please enter valid email.',
+ 'photo.mimes' => 'The profile image must be a file of type: jpeg, jpg, png.',
+ 'role_id.required' => 'Please select user role.',
];
public static $setPasswordRules = [
diff --git a/app/Repositories/DashboardRepository.php b/app/Repositories/DashboardRepository.php
index f96150a04..334a28f64 100644
--- a/app/Repositories/DashboardRepository.php
+++ b/app/Repositories/DashboardRepository.php
@@ -66,7 +66,7 @@ public function getWorkReport($input)
$result = [];
// preparing a date array for displaying a labels
foreach ($dates['dateArr'] as $date) {
- $date = date('d-M', strtotime($date));
+ $date = date('jS M', strtotime($date));
$result['date'][] = $date;
}
$result['projects'] = array_keys($projects);
diff --git a/app/Repositories/ReportRepository.php b/app/Repositories/ReportRepository.php
index a61abb802..a562ddff2 100644
--- a/app/Repositories/ReportRepository.php
+++ b/app/Repositories/ReportRepository.php
@@ -266,6 +266,8 @@ public function getReport($report)
$project = $entry->task->project;
$client = $project->client;
$duration = $entry->duration;
+ $projectPrefix = $project->prefix;
+ $taskNumber = $entry->task->task_number;
// prepare client and duration
$result[$clientId]['name'] = $client->name;
@@ -306,6 +308,8 @@ public function getReport($report)
$time = $result[$clientId]['projects'][$project->id]['users'][$entry->user_id]['tasks'][$entry->task_id]['duration'] + $entry->duration;
$result[$clientId]['projects'][$project->id]['users'][$entry->user_id]['tasks'][$entry->task_id]['duration'] = $time;
$result[$clientId]['projects'][$project->id]['users'][$entry->user_id]['tasks'][$entry->task_id]['time'] = $this->getDurationTime($time);
+ $result[$clientId]['projects'][$project->id]['users'][$entry->user_id]['tasks'][$entry->task_id]['project_prefix'] = $projectPrefix;
+ $result[$clientId]['projects'][$project->id]['users'][$entry->user_id]['tasks'][$entry->task_id]['task_number'] = $taskNumber;
}
return $result;
diff --git a/composer.json b/composer.json
index 7e1a902ee..39e157dd9 100644
--- a/composer.json
+++ b/composer.json
@@ -1,7 +1,7 @@
{
"name": "infyomlabs/infy-tracker",
"type": "project",
- "version": "1.8.1-alpha",
+ "version": "1.8.2-alpha",
"description": "Create Projects / Tasks, Track Time, Show Daily Reports",
"keywords": [
"time",
diff --git a/database/factories/ReportFactory.php b/database/factories/ReportFactory.php
index 89e0ffbd8..27b74f0b2 100644
--- a/database/factories/ReportFactory.php
+++ b/database/factories/ReportFactory.php
@@ -8,11 +8,13 @@
$factory->define(Report::class, function (Faker $faker) {
$user = factory(User::class)->create();
+ $startDate = date('Y-m-d H:i:s', strtotime('-1 day'));
+ $endDate = date('Y-m-d H:i:s');
return [
'name' => $faker->word,
'owner_id' => $user->id,
- 'start_date' => $faker->dateTime,
- 'end_date' => $faker->dateTime,
+ 'start_date' => $startDate,
+ 'end_date' => $endDate,
];
});
diff --git a/database/factories/TaskFactory.php b/database/factories/TaskFactory.php
index 46a58a230..1fec508ac 100644
--- a/database/factories/TaskFactory.php
+++ b/database/factories/TaskFactory.php
@@ -10,12 +10,15 @@
$factory->define(Task::class, function (Faker $faker) {
$project = factory(Project::class)->create();
+ $dueDate = date('Y-m-d H:i:s', strtotime('+ 4hours'));
+
+ $dueDate = date('Y-m-d H:i:s', strtotime('+ 4hours'));
return [
'title' => $faker->sentence,
'description' => $faker->text,
'project_id' => $project->id,
- 'due_date' => $faker->dateTime,
+ 'due_date' => $dueDate,
'status' => Task::STATUS_ALL,
'task_number' => $faker->unique()->randomDigitNotNull,
];
diff --git a/database/factories/UserFactory.php b/database/factories/UserFactory.php
index eee07d140..dce948130 100644
--- a/database/factories/UserFactory.php
+++ b/database/factories/UserFactory.php
@@ -22,5 +22,8 @@
'email_verified_at' => now(),
'password' => '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi', // password
'remember_token' => Str::random(10),
+ 'is_active' => true,
+ 'is_email_verified' => true,
+ 'set_password' => true,
];
});
diff --git a/resources/assets/js/custom.js b/resources/assets/js/custom.js
index d1bf03c29..35922a485 100644
--- a/resources/assets/js/custom.js
+++ b/resources/assets/js/custom.js
@@ -165,3 +165,32 @@ window.displaySuccessMessage = function (message) {
position: 'top-right',
});
};
+
+$(function () {
+ $(".dataTables_length").css('padding-top', '6px');
+ $(".dataTables_info").css('padding-top', '24px');
+});
+
+$.extend($.fn.dataTable.defaults, {
+ drawCallback: function (settings) {
+ let thisTableId = settings.sTableId;
+ if (settings.fnRecordsDisplay() > settings._iDisplayLength) {
+ $('#' + thisTableId + '_paginate').show();
+ } else {
+ $('#' + thisTableId + '_paginate').hide();
+ }
+ }
+});
+
+//focus on select2
+$(document).on('focus', '.select2-selection.select2-selection--single', function (e) {
+ $(this).closest(".select2-container").siblings('select:enabled').select2('open');
+});
+
+$(function () {
+ $(".modal").on('shown.bs.modal', function () {
+ setTimeout(function () {
+ $(".modal").find('input:text, .select2-selection.select2-selection--single').first().focus();
+ },150);
+ });
+});
diff --git a/resources/assets/js/dashboard/dashboard.js b/resources/assets/js/dashboard/dashboard.js
index 0ae2fd7a0..d5553e820 100644
--- a/resources/assets/js/dashboard/dashboard.js
+++ b/resources/assets/js/dashboard/dashboard.js
@@ -20,7 +20,7 @@ timeRange.on('apply.daterangepicker', function (ev, picker) {
});
window.cb = function (start, end) {
- timeRange.find('span').html(start.format('MMMM D, YYYY') + ' - ' + end.format('MMMM D, YYYY'));
+ timeRange.find('span').html(start.format('MMM D, YYYY') + ' - ' + end.format('MMM D, YYYY'));
};
cb(start, end);
@@ -67,7 +67,6 @@ window.loadUserWorkReport = function (startDate, endDate, userId) {
window.prepareUserWorkReport = function (result) {
$('#daily-work-report').html('');
let data = result.data;
- console.log(result);
if (data.totalRecords === 0) {
$('#work-report-container').html('');
$('#work-report-container').append('
No Records Found
');
@@ -96,12 +95,15 @@ window.prepareUserWorkReport = function (result) {
mode: 'index',
callbacks: {
label: function (tooltipItem, data) {
+ result = roundToQuarterHour(tooltipItem.yLabel);
+ if(result == '0min') {
+ return '';
+ }
let label = data.datasets[tooltipItem.datasetIndex].label || '';
if (label) {
label += ': ';
}
- result = roundToQuarterHour(tooltipItem.yLabel);
return label + result;
}
}
diff --git a/resources/assets/js/dashboard/developers-daily-report.js b/resources/assets/js/dashboard/developers-daily-report.js
index cfd0d3719..a763e45cc 100644
--- a/resources/assets/js/dashboard/developers-daily-report.js
+++ b/resources/assets/js/dashboard/developers-daily-report.js
@@ -11,7 +11,7 @@ $datePicker.on('apply.daterangepicker', function (ev, picker) {
});
window.cb = function (start) {
- $datePicker.find('span').html(start.format('MMMM D, YYYY'));
+ $datePicker.find('span').html(start.format('MMM D, YYYY'));
};
cb(start);
diff --git a/resources/assets/js/profile/profile.js b/resources/assets/js/profile/profile.js
index a9d83f822..a01fd1513 100644
--- a/resources/assets/js/profile/profile.js
+++ b/resources/assets/js/profile/profile.js
@@ -4,7 +4,7 @@ $('#editProfileForm').submit(function (event) {
if(!isValidate){
return false;
}
- let loadingButton = jQuery(this).find("#btnEditSave");
+ let loadingButton = jQuery(this).find("#btnPrEditSave");
loadingButton.button('loading');
$.ajax({
url: usersUrl + 'profile-update',
@@ -120,4 +120,14 @@ function validatePassword() {
return false;
}
return true;
-}
\ No newline at end of file
+}
+
+$(".changeType").click(function () {
+ let inputField = $(this).parent().siblings();
+ let oldType = inputField.attr('type');
+ if(oldType == 'password') {
+ inputField.attr('type', 'text');
+ } else {
+ inputField.attr('type', 'password');
+ }
+});
diff --git a/resources/assets/js/report/report.js b/resources/assets/js/report/report.js
index e2a152a06..dcd8c3509 100644
--- a/resources/assets/js/report/report.js
+++ b/resources/assets/js/report/report.js
@@ -44,6 +44,10 @@ $('#end_date').datetimepicker({
maxDate: moment()
});
+$(function () {
+ $('form').find('input:text').filter(':input:visible:first').first().focus();
+});
+
$("#start_date").on("dp.change", function (e) {
$('#end_date').data("DateTimePicker").minDate(e.date);
});
diff --git a/resources/assets/js/task/task.js b/resources/assets/js/task/task.js
index c139adec1..187bb9a1f 100644
--- a/resources/assets/js/task/task.js
+++ b/resources/assets/js/task/task.js
@@ -318,9 +318,9 @@ $(document).on('change', '#task_users', function () {
taskId = taskUserId[1];
userId = taskUserId[0];
}
- let url = taskDetailUrl + '/' + taskId
+ let url = taskDetailUrl + '/' + taskId;
if (userId !== 0) {
- url = url + '?user_id=' + userId
+ url = url + '?user_id=' + userId;
}
$.ajax({
url: url,
@@ -374,7 +374,8 @@ window.drawTaskDetailTable = function (data) {
$('#no-record-info-msg').hide();
stopLoader();
- $('#taskDetailsTable tbody').on('click', 'td.details-control', function () {
+ $('#taskDetailsTable tbody').off('click', 'tr td.details-control');
+ $('#taskDetailsTable tbody').on('click', 'tr td.details-control', function () {
var tr = $(this).closest('tr');
var row = taskDetailsTable.row(tr);
@@ -384,7 +385,7 @@ window.drawTaskDetailTable = function (data) {
tr.removeClass('shown');
} else {
// Open this row
- row.child(formatCollapsableRow(row.data())).show();
+ row.child('' + row.data().note + '
').show();
tr.addClass('shown');
}
});
diff --git a/resources/assets/js/task/task_detail.js b/resources/assets/js/task/task_detail.js
index 84d08c33f..23df41144 100644
--- a/resources/assets/js/task/task_detail.js
+++ b/resources/assets/js/task/task_detail.js
@@ -239,11 +239,10 @@ Dropzone.options.dropzone = {
let newFileName = fileNameExtArr[0];
let newFileExt = fileNameExtArr[1];
let prevFileName = fileuploded.innerHTML.split('.')[0];
- let fileUrl = attachmentUrl + fileName;
fileuploded.innerHTML = fileName;
- $(".dz-preview:last-child").children(':last-child').attr('data-file-id', attachment.id);
- $(".dz-preview:last-child").children(':last-child').attr('data-file-url', attachment.file_url);
+ $(file.previewTemplate).find('.dz-remove').attr('data-file-id', attachment.id);
+ $(file.previewTemplate).find('.dz-remove').attr('data-file-url', attachment.file_url);
if($.inArray(newFileExt,['jpg','jpge','png']) > -1) {
$(".previewEle").find('.' + prevFileName).attr('href', attachment.file_url);
$(".previewEle").find('.' + prevFileName).attr('class', newFileName);
diff --git a/resources/assets/js/time_entries/time_entry.js b/resources/assets/js/time_entries/time_entry.js
index 5ad667a39..66dfb0bf6 100644
--- a/resources/assets/js/time_entries/time_entry.js
+++ b/resources/assets/js/time_entries/time_entry.js
@@ -261,6 +261,7 @@ $('#startTime,#endTime').on('dp.change', function (selected) {
$('#startTime').data("DateTimePicker").maxDate(moment().endOf('now'));
$('#endTime').data("DateTimePicker").maxDate(moment().endOf('now'));
});
+$('#endTime').val(moment().format('YYYY-MM-DD HH:mm:ss'));
$('#editTimeEntryForm').submit(function (event) {
event.preventDefault();
diff --git a/resources/assets/js/time_tracker/time_tracker.js b/resources/assets/js/time_tracker/time_tracker.js
index 05fe3b4eb..d676bb53e 100644
--- a/resources/assets/js/time_tracker/time_tracker.js
+++ b/resources/assets/js/time_tracker/time_tracker.js
@@ -191,7 +191,7 @@ $("#stopTimer").click(function (e) {
enableTimerData();
$('#loader').show();
- storeTimeEntry();
+ checkTimeEntry();
});
function enableTimerData() {
@@ -215,10 +215,102 @@ function stopTime() {
seconds = minutes = hours = 0;
}
-function storeTimeEntry() {
+function diff_mins(dt2, dt1) {
+ dt2 = new Date(dt2);
+ dt1 = new Date(dt1);
+ var diff = (dt2.getTime() - dt1.getTime()) / 1000;
+ diff /= (60);
+ return Math.abs(Math.round(diff));
+}
+
+function adjustTimeEntry() {
+ let startDate = getItemFromLocalStorage('start_time');
+ $("#tmAdjustValidationErrorsBox").show();
+ $("#tmAdjustValidationErrorsBox").html("Time Entry must be less than 12 hours.");
+ $('#adjustStartTime').val(startDate);
+ $('#adjustStartTime').attr('disabled', 'true');
+ $("#timeEntryAdjustModal").modal();
+ $('#stopTimer').removeAttr('disabled');
+}
+
+$('#timeEntryAdjustModal').on('hidden.bs.modal', function () {
+ $('#adjustEndTime').prop('disabled', false);
+ $('#adjustStartTime').prop('disabled', false);
+ $("#adjustEndTime").data("DateTimePicker").date(null);
+ $("#adjustStartTime").data("DateTimePicker").date(null);
+ resetModalForm('#timeEntryAdjustForm');
+ $('#tmAdjustValidationErrorsBox').hide();
+});
+
+$('#adjustStartTime').datetimepicker({
+ format: 'YYYY-MM-DD HH:mm:ss',
+ useCurrent: true,
+ icons: {
+ up: "icon-arrow-up icons",
+ down: "icon-arrow-down icons",
+ previous: 'icon-arrow-left icons',
+ next: 'icon-arrow-right icons',
+ },
+ sideBySide: true,
+ maxDate: moment().endOf('day'),
+});
+$('#adjustEndTime').datetimepicker({
+ format: 'YYYY-MM-DD HH:mm:ss',
+ useCurrent: true,
+ icons: {
+ up: "icon-arrow-up icons",
+ down: "icon-arrow-down icons",
+ previous: 'icon-arrow-left icons',
+ next: 'icon-arrow-right icons',
+ },
+ sideBySide: true,
+ maxDate: moment().endOf('day'),
+});
+
+$('#adjustStartTime,#adjustEndTime').on('dp.change', function () {
+ const startTime = $('#adjustStartTime').val();
+ const endTime = $('#adjustEndTime').val();
+ let minutes = 0;
+ if (endTime) {
+ const diff = new Date(Date.parse(endTime) - Date.parse(startTime));
+ minutes = diff / (1000 * 60);
+ if (!Number.isInteger(minutes)) {
+ minutes = minutes.toFixed(2);
+ }
+ }
+ $('#adjustDuration').val(minutes).prop('disabled', true);
+ $('#adjustStartTime').data("DateTimePicker").maxDate(moment().endOf('now'));
+ $('#adjustEndTime').data("DateTimePicker").maxDate(moment().endOf('now'));
+ if(minutes < 720) {
+ $('#tmAdjustValidationErrorsBox').hide();
+ }
+});
+
+$('#adjustBtnSave').click(function () {
+ let startTime = $('#adjustStartTime').val();
+ let endTime = $('#adjustEndTime').val();
+ let totalMin = diff_mins(endTime, startTime);
+ if(totalMin > 720) {
+ $("#tmAdjustValidationErrorsBox").show();
+ $("#tmAdjustValidationErrorsBox").html("Time Entry must be less than 12 hours.");
+ } else {
+ $("#adjustBtnCancel").trigger('click');
+ storeTimeEntry(startTime, endTime);
+ }
+});
+
+function checkTimeEntry() {
let startTime = getItemFromLocalStorage('start_time');
let endTime = getCurrentTime();
+ let totalMin = diff_mins(endTime, startTime);
+ if(totalMin > 720) {
+ adjustTimeEntry();
+ } else {
+ storeTimeEntry(startTime, endTime);
+ }
+}
+function storeTimeEntry(startTime, endTime) {
$.ajax({
url: storeTimeEntriesUrl,
type: 'POST',
diff --git a/resources/assets/js/users/user.js b/resources/assets/js/users/user.js
index a6cd92def..0e8bcfb73 100644
--- a/resources/assets/js/users/user.js
+++ b/resources/assets/js/users/user.js
@@ -4,7 +4,8 @@ $(function () {
});
$('#roleId,#editRoleId').select2({
width: '100%',
- placeholder: "Select Role"
+ placeholder: "Select Role",
+ minimumResultsForSearch: -1
});
});
diff --git a/resources/assets/style/sass/style.scss b/resources/assets/style/sass/style.scss
index b42637b49..25ef0ac9a 100644
--- a/resources/assets/style/sass/style.scss
+++ b/resources/assets/style/sass/style.scss
@@ -483,7 +483,7 @@ table.dataTable {
}
.edit-profile__file-upload {
- padding: 10px;
+ padding: 7px 10px;
background: #20a8d8;
display: table;
color: $white;
@@ -550,3 +550,9 @@ table.dataTable {
overflow-y: auto;
max-height: 750px;
}
+
+.input-group__addon {
+ border-top-right-radius: 0 !important;
+ border-bottom-right-radius: 0 !important;
+}
+
diff --git a/resources/views/dashboard/index.blade.php b/resources/views/dashboard/index.blade.php
index 05427369b..f2771ac45 100644
--- a/resources/views/dashboard/index.blade.php
+++ b/resources/views/dashboard/index.blade.php
@@ -28,11 +28,11 @@
@permission('manage_users')
-
+
{!! Form::select('users', $users, Auth::id(), ['id' => 'userId','class'=>'user_filter_dropdown']) !!}
@endpermission
-
+
+
+
@yield('page_css')
@yield('css')
@@ -70,6 +74,7 @@
@include('time_tracker.index');
+@include('time_tracker.adjust_time_entry');