George Richardson
George Richardson

Reputation: 49

Calculate working days from a original date

What we need:

example Customer start date is 11th March 2019 - 28 working days equals to 18th April , the 18th April becomes the month 1 end date, Month 2 start date is 18th April (month 1 end date + 1) which is equal to 19th April, then month 2 end date is +28 working days ... so forth for the next 12 months we need the end and start dates.

Can we also have it so its just the dates displayed and not (time and greenwhich) at the end of the date

I have so far a simple js 28-working day script that works ... but I don't know how to do the complex bit, I tried grabbing the element with html and re doing the script but it didn't work as planned.

May someone help with this struggule. Many thanks.

var startDate = "2019-03-11";
startDate = new Date(startDate.replace(/-/g, "/"));
var endDate = "", noOfDaysToAdd = 28, count = 0;
while(count < noOfDaysToAdd){
    endDate = new Date(startDate.setDate(startDate.getDate() + 1));
    if(endDate.getDay() != 0 && endDate.getDay() != 6){
       count++;
    }
}

document.getElementById("month1end").value = endDate;

Upvotes: 0

Views: 533

Answers (2)

trincot
trincot

Reputation: 350272

Here is how you could do it. Note that to get the last day of a "month" of 28 working days, you need to add 27 working days to the first day (not 28). Adding 28 will give you the first day of the next month.

I would suggest using a function that adds a number of working days to a give date (object). It will ensure the result is a working day. So even if you add 0 days, it might change the date (when it was a weekend day).

Here is the function, and the additional code to generate the 12 months, and also support for bank holidays. Just define them in the first assignment:

const bankHolidays = new Set([
    Date.parse("April, 19 2019"), 
    Date.parse("April, 22 2019")
]);
function addWorkingDays(date, days) {
    function workingDay(date) {
        while (true) {
            let day = (date.getDay() + 1) % 7;
            if (day < 2) date.setDate(date.getDate() + 2 - day);
            if (!bankHolidays.has(date.getTime())) break; 
            date.setDate(date.getDate()+1);
        }
    }
    workingDay(date);
    while(days--) {
        date.setDate(date.getDate() + 1);
        workingDay(date);
    }
    return date;
}

document.querySelector("button").addEventListener("click", function() {
    const dateStr = document.querySelector("#startdate").value.replace(/-/g, "/");
    const date = new Date(dateStr);
    addWorkingDays(date, 0); // Make sure it is a working day
    const td = document.querySelectorAll("td");
    for (let i = 0; i < 12; i++) {
        td[i*2].textContent = date.toDateString();
        td[i*2+1].textContent = addWorkingDays(date, 27).toDateString();
        addWorkingDays(date, 1);
    }
});
table, tr, td, th {
  border: 1px solid;
  border-collapse: collapse;
}
<label>Start date: <input id="startdate"></label>
<button>Generate months</button>

<table>
    <tr><th>start</th><th>end</th></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
    <tr><td></td><td></td></tr>
</table>

Upvotes: 1

Tomal
Tomal

Reputation: 127

Since this date can be converted to milisecounds by signing it to variable, you can just simply add one day in ms, so you will get your '19th April', or try this endDate.setDate(endDate.getDate() + 1) - will work as well i think.

If you want to do this automatically for 12 month just put your code in a loop and change start day after each iteration.

Hope i helped.

Upvotes: 0

Related Questions