|
|
|
@@ -147,11 +147,13 @@ |
|
|
|
if (response.status =='success'){ |
|
|
|
bts().staff = response.users; |
|
|
|
bts().staff_map = {}; |
|
|
|
bts().staff_people= {}; |
|
|
|
response.users.forEach(function(u){ |
|
|
|
bts().staff_map[u.login] = u; |
|
|
|
var html = bts_staff_html(u); |
|
|
|
jQuery('div.stafflist').append(html); |
|
|
|
new People("#p" + u.login,'#staff_item', u); |
|
|
|
var staff_obj = new People("#p" + u.login,'#staff_item', u); |
|
|
|
bts().staff_people[u.login] = staff_obj; |
|
|
|
}); |
|
|
|
hide_loading_staff(); |
|
|
|
calculate_total_hour_and_money(); |
|
|
|
@@ -304,6 +306,9 @@ |
|
|
|
jobid: id, |
|
|
|
}, function(response, status, xhr){ |
|
|
|
if (response.status=='success'){ |
|
|
|
var id = el.attr('data-id'); |
|
|
|
delete bts().job_map[id]; |
|
|
|
console.log("delete %s , job_map[%d]=%o ", id, id, bts().job_map[id]); |
|
|
|
el.addClass('blink_me'); |
|
|
|
el.fadeOut(900); |
|
|
|
setTimeout(function(){ |
|
|
|
@@ -1187,10 +1192,13 @@ |
|
|
|
(typeof b.tos != "undefined" && Object.keys(b.tos).length > 0 ) && |
|
|
|
(typeof b.earnings_rate != "undefined" && Object.keys(b.earnings_rate).length > 0 )) |
|
|
|
{ |
|
|
|
var job_map={}; |
|
|
|
//map data for each jobTable |
|
|
|
response.jobs.forEach(function(e){ |
|
|
|
job_derive_attr(e); |
|
|
|
job_map[e.id] = e; |
|
|
|
}); |
|
|
|
bts().job_map = job_map; |
|
|
|
|
|
|
|
//we do works, load timesheets |
|
|
|
var template = $("#jobv1_item").html(); |
|
|
|
@@ -1217,6 +1225,7 @@ |
|
|
|
|
|
|
|
if (! has_txt_hour( bts().earnings_rate[e.rate].TypeOfUnits )){ |
|
|
|
e.non_hour = true; |
|
|
|
e.brate_err = "Rate type is not Hours - Not allowed"; |
|
|
|
} |
|
|
|
|
|
|
|
if (job_is_week1(e.start)){ |
|
|
|
@@ -1402,18 +1411,19 @@ |
|
|
|
|
|
|
|
if (hide_week1 && hide_week2 ){ |
|
|
|
alert("You are hiding both weeks"); |
|
|
|
$('div.jobTable').show();//show non-week1 and none-week2 |
|
|
|
$('div.jobTable.week1job,div.jobTable.week2job').hide(); //hide week1 or week2; |
|
|
|
}else if (hide_week1){ |
|
|
|
$('div.jobTable:not(.week1job)').show();//show non-week1 |
|
|
|
$('div.jobTable.week1job').hide(); //hide week1; |
|
|
|
}else if (hide_week2){ |
|
|
|
$('div.jobTable.week2job').hide(); //show non-week2 |
|
|
|
$('div.jobTable:not(.week2job)').show(); //hide week2 |
|
|
|
} |
|
|
|
|
|
|
|
$('div.workspace div.divTable').each(function(i,e){ |
|
|
|
var job = $(e).data().job; |
|
|
|
if ((hide_week1 && job.is_week1()) || |
|
|
|
(hide_week2 && job.is_week2()) ){ |
|
|
|
$(e).fadeOut(); |
|
|
|
} |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
var debounced_calculate = debounce(calculate_total_hour_and_money, 2000); |
|
|
|
var debounced_calculate = debounce(calculate_total_hour_and_money, 500); |
|
|
|
|
|
|
|
function calculate_total_hour_and_money() |
|
|
|
{ |
|
|
|
@@ -1427,20 +1437,21 @@ |
|
|
|
people.reset_summary(); |
|
|
|
}); |
|
|
|
|
|
|
|
$('div.workspace > .divTable').each(function(i,e){ |
|
|
|
$('div.workspace > .divTable.jobTable').each(function(i,e){ |
|
|
|
if (! $(e).is(':visible')) |
|
|
|
return; |
|
|
|
|
|
|
|
var job = $(e).data().job; //class Job |
|
|
|
var id = $(e).attr('data-id'); |
|
|
|
var job = bts().job_map[id]; |
|
|
|
if (typeof job === 'undefined') |
|
|
|
return; |
|
|
|
var ps = job.get_payment_summary(); |
|
|
|
var ps = job_get_payment_summary(job); |
|
|
|
|
|
|
|
pays.total += ps.money; |
|
|
|
pays.hours += ps.hour; |
|
|
|
|
|
|
|
var staff = job.get_staff(); |
|
|
|
var people = find_staff(staff); //class People |
|
|
|
var staff = job.staff; |
|
|
|
var people = bts().staff_people[staff]; //class People |
|
|
|
if (people !=false) |
|
|
|
people.add_payment_summary(ps); |
|
|
|
}); |
|
|
|
@@ -1448,6 +1459,56 @@ |
|
|
|
set_working_hours(pays.hours.toFixed(2)); |
|
|
|
} |
|
|
|
|
|
|
|
function job_get_payment_summary(job) |
|
|
|
{ |
|
|
|
var result ={}; |
|
|
|
result.ot = job_get_is_high_pay(job); |
|
|
|
result.hour = job_get_working_duration(job); |
|
|
|
result.money = job_get_wages(job); |
|
|
|
return result; |
|
|
|
} |
|
|
|
|
|
|
|
function job_get_is_high_pay(job) |
|
|
|
{ |
|
|
|
var rate_info = bts().earnings_rate[job.rate]; |
|
|
|
|
|
|
|
var keywords =bts().high_pay_keywords; |
|
|
|
var found = false; |
|
|
|
keywords.forEach(function(e){ |
|
|
|
if (-1 != rate_info.Name.toLowerCase().indexOf(e.toLowerCase()) ) |
|
|
|
found = true; |
|
|
|
}); |
|
|
|
return found; |
|
|
|
} |
|
|
|
|
|
|
|
function job_get_working_duration(job) |
|
|
|
{ |
|
|
|
//finish - start |
|
|
|
var f = new Date(job.finish); |
|
|
|
var s = new Date(job.start); |
|
|
|
var diff = f.getTime() - s.getTime(); |
|
|
|
var hours = Math.floor(diff / 1000 / 60 / 60); |
|
|
|
diff -= hours * 1000 * 60 * 60; |
|
|
|
var minutes = Math.floor(diff / 1000 / 60); |
|
|
|
var minute_to_hour = minutes/60; |
|
|
|
return (hours + minute_to_hour); |
|
|
|
} |
|
|
|
|
|
|
|
function job_get_wages(job) |
|
|
|
{ |
|
|
|
var hour = job_get_working_duration(job); |
|
|
|
var rate_info = bts().earnings_rate[job.rate]; |
|
|
|
if ( has_txt_hour( bts().earnings_rate[job.rate].TypeOfUnits ) ) |
|
|
|
{ |
|
|
|
return hour * rate_info.RatePerUnit; |
|
|
|
}else{ |
|
|
|
return 1 * rate_info.RatePerUnit; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function find_staff(login) |
|
|
|
{ |
|
|
|
var d = $('#p'+login).data(); |
|
|
|
@@ -1578,11 +1639,62 @@ |
|
|
|
response.options.forEach(function(e){ |
|
|
|
bts().earnings_rate[e.EarningsRateID]=e; |
|
|
|
}); |
|
|
|
console.log("%o", bts().earnings_rate); |
|
|
|
//console.log("%o", bts().earnings_rate); |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
function check_duplicate() |
|
|
|
{ |
|
|
|
var count= 0; |
|
|
|
var to_be_delete=[]; |
|
|
|
//loop through jobs |
|
|
|
for(var id1 in bts().job_map){ |
|
|
|
var job1 = bts().job_map[id1]; |
|
|
|
if (typeof job1.parent != 'undefined') |
|
|
|
continue; //bypass it it has already found parents |
|
|
|
|
|
|
|
job1.compared_as_master = true;//mark it |
|
|
|
job1.duplicates={}; |
|
|
|
//console.log('investigating %s' , job1.id); |
|
|
|
//match job2 |
|
|
|
for(var id2 in bts().job_map){ |
|
|
|
var job2 = bts().job_map[id2]; |
|
|
|
if (typeof job2.compared_as_master != 'undefined') |
|
|
|
continue; |
|
|
|
|
|
|
|
if (typeof job2.parent != "undefined") |
|
|
|
continue; //it has already parent; |
|
|
|
//console.log('comareing %s vs %s', job1.id, job2.id); |
|
|
|
if (is_same_job(job1,job2)){ |
|
|
|
job2.parent = job1.id; |
|
|
|
job1.duplicates[id2] = job2; |
|
|
|
console.warn("found: %s = %s", job1.id, job2.id); |
|
|
|
count++; |
|
|
|
to_be_delete.push(id2); |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
console.log('all-done, found %d duplicates: %o', count, to_be_delete); |
|
|
|
} |
|
|
|
|
|
|
|
$('div.wages').click(check_duplicate); |
|
|
|
|
|
|
|
function is_same_job(job1, job2) |
|
|
|
{ |
|
|
|
if ( (job1.tos == job2.tos) && |
|
|
|
(job1.staff == job2.staff) && |
|
|
|
(job1.client == job2.client) && |
|
|
|
(job1.start == job2.start) && |
|
|
|
(job1.finish == job2.finish) ) |
|
|
|
{ |
|
|
|
return true; |
|
|
|
} |
|
|
|
return false; |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
$( ".boundary_datepicker" ).datepicker(); |
|
|
|
$( ".boundary_datepicker" ).datepicker("option", "dateFormat", "yy-mm-dd"); |
|
|
|
|