When you create a calendar, like OOoCalendar, it’s nice, if the calendar already calculates holidays. One of the holidays, that is every year on a somewhat different date is Easter. There are many other Christian holidays that depend on the Easter day like 40 days after Easter is Ascension Day.

The book “Astronomical Algorithms” by Jean Meeus provides an algorithm, that is claimed to be valid without any exceptions from the year 1583. In 1582, there was the Gregorian calendar reform, which jumped a couple of days in October 1582. But after that, the formula should produce correct results.

It takes a couple of divisions, until you get the date. You start with the year x.

Divide by QuotientRemainder
the year x 19 - a
the year x 100b c
b 4 d e
b + 8 25 f -
b - f + 1 3 g -
19a + b - d - g + 1530 - h
c 4 i k
32 + 2e + 2i - h - k7 - l
a + 11h + 22l 451m -
h + l - 7m + 114 31 n p

After these calculations, n is the number of the month (3 = March, 4 = April), and p+1 is the day of that month upon which Easter Sunday falls.

In general, this is the rule for finding Easter Sunday:

Easter Sunday is the first Sunday after the Full Moon that happens on or next after the March equinox.

(page 68, Astronomical Algorithms by Jean Meeus, 2nd edition)

To make the rules a bit easier (and less astronomical correct), the equinox is assumed to fall on March 21 always. In reality, it can also be one or two days earlier. Also the full moon is simplified and uses an ecclesiastical computation.

Sample results

  • 1991 -> March 31
  • 1992 -> April 19
  • 1993 -> April 11
  • 1954 -> April 18
  • 2000 -> April 23
  • 2017 -> April 16
  • 1818 -> March 22
  • 2018 -> ???

Try it out…

Year:

Here’s the JS snippet:

function calculateEasterDate(year) {
    // http://stackoverflow.com/questions/4228356/how-to-perform-integer-division-and-get-the-remainder-in-javascript
    var intDiv = function(a, b) { return (a/b>>0); }
    var a = year % 19;
    var b = intDiv(year, 100);
    var c = year % 100;
    var d = intDiv(b, 4);
    var e = b % 4;
    var f = intDiv(b + 8, 25);
    var g = intDiv(b - f + 1, 3);
    var h = (19*a + b - d - g + 15) % 30;
    var i = intDiv(c, 4);
    var k = c % 4;
    var l = (32 + 2*e + 2*i - h - k) % 7;
    var m = intDiv(a + 11*h + 22*l, 451);
    var n = intDiv(h + l - 7*m + 114, 31);
    var p = (h + l - 7*m + 114) % 31;

    var month = "unknown";
    if (n == 3) month = "March";
    if (n == 4) month = "April";

    return {
        month: n,
        day: p + 1,
        text: 'Easter Sunday in ' + year + ' is on ' + month + ' ' + (p + 1) + '.'
    };
}