DateTime-Calendar-Liturgical-Christian
view release on metacpan or search on metacpan
lib/DateTime/Calendar/Liturgical/Christian.pm view on Meta::CPAN
my($c) = $y/100;
my($g) = $y % 19;
my($k) = ($c-17)/25;
my($i) = ($c - $c/4 - ($c-$k)/3 + 19*$g + 15) % 30;
$i = $i - ($i/28)*(1 - ($i/28)*(29/($i+1))*((21-$g)/11));
my($j) = ($y + $y/4 + $i + 2 - $c + $c/4) % 7;
my($l) = $i-$j;
my($m) = 3 + ($l+40)/44;
my($d) = $l + 28 - 31*($m/4);
return ($m,$d);
}
sub advent_sunday {
my ($y) = @_;
return -(Day_of_Week($y,12,25) + 4*7);
}
##########################################################################
sub new {
my ($class, %opts) = @_;
my $y = $opts{year};
my $m = $opts{month};
my $d = $opts{day};
die "Need to specify year, month and day" unless $y and $m and $d;
my $days = Date_to_Days($y, $m, $d);
my $easter = Date_to_Days($y, Date_Easter($y));
my @possibles;
# "The Church Year consists of two cycles of feasts and holy days: one is
# dependent upon the movable date of the Sunday of the Resurrection or
# Easter Day; the other, upon the fixed date of December 25, the Feast
# of our Lord's Nativity or Christmas Day."
my $easter_point = $days-$easter;
my $christmas_point;
# We will store the amount of time until (-ve) or since (+ve) Christmas in
# $christmas_point. Let's make the cut-off date the end of February,
# since we'll be dealing with Easter-based dates after that, and it
# avoids the problems of considering leap years.
if ($m>2) {
$christmas_point = $days - Date_to_Days($y, 12, 25);
} else {
$christmas_point = $days - Date_to_Days($y-1, 12, 25);
}
# First, figure out the season.
my ($season, $weekno);
my $advent_sunday = advent_sunday($y);
if ($easter_point>-47 && $easter_point<0) {
$season = 'Lent';
$weekno = ($easter_point+50)/7;
# FIXME: The ECUSA calendar seems to indicate that Easter Eve ends
# Lent *and* begins the Easter season. I'm not sure how. Maybe it's
# in both? Maybe the daytime is in Lent and the night is in Easter?
} elsif ($easter_point>=0 && $easter_point<=49) {
# yes, this is correct: Pentecost itself is in Easter season;
# Pentecost season actually begins on the day after Pentecost.
# Its proper name is "The Season After Pentecost".
$season = 'Easter';
$weekno = $easter_point/7;
} elsif ($christmas_point>=$advent_sunday && $christmas_point<=-1) {
$season = 'Advent';
$weekno = 1+($christmas_point-$advent_sunday)/7;
} elsif ($christmas_point>=0 && $christmas_point<=11) {
# The Twelve Days of Christmas.
$season = 'Christmas';
$weekno = 1+$christmas_point/7;
} elsif ($christmas_point>=12 && $easter_point <= -47) {
$season = 'Epiphany';
$weekno = 1+($christmas_point-12)/7;
} else {
$season = 'Pentecost';
$weekno = 1+($easter_point-49)/7;
}
# Now, look for feasts.
my $feast_from_Easter = $feasts{$easter_point};
my $feast_from_Christmas = $feasts{10000+100*$m+$d};
push @possibles, $feast_from_Easter if $feast_from_Easter;
push @possibles, $feast_from_Christmas if $feast_from_Christmas;
# Maybe transferred from yesterday.
unless ($opts{transferred}) { # don't go round infinitely
my ($yestery, $yesterm, $yesterd) = Add_Delta_Days(1, 1, 1, $days-2);
my $transferred = $class->new(
%opts,
year => $yestery,
month => $yesterm,
day => $yesterd,
transferred=>1,
);
if ($transferred) {
$transferred->{name} .= ' (transferred)';
push @possibles, $transferred;
}
}
# Maybe a Sunday.
push @possibles, { prec=>5, name=>"$season $weekno" }
if Day_of_Week($y, $m, $d)==7;
# So, which event takes priority?
@possibles = sort { $b->{prec} <=> $a->{prec} } @possibles;
if ($opts{transferred}) {
# If two feasts coincided today, we were asked to find
lib/DateTime/Calendar/Liturgical/Christian.pm view on Meta::CPAN
# Two special cases for Christmas-based festivals which
# depend on the day of the week.
if ($result->{prec} == 5) { # An ordinary Sunday
if ($christmas_point == $advent_sunday) {
$result->{name} = 'Advent Sunday';
$result->{colour} = 'white';
} elsif ($christmas_point == $advent_sunday-7) {
$result->{name} = 'Christ the King';
$result->{colour} = 'white';
}
}
return bless($result, $class);
}
sub year { my ($self)=@_; return $self->{year}; }
sub month { my ($self)=@_; return $self->{month}; }
sub day { my ($self)=@_; return $self->{day}; }
sub colour { my ($self)=@_; return $self->{colour}; }
sub color { goto &colour; }
sub season { my ($self)=@_; return $self->{season}; }
sub name { my ($self)=@_; return $self->{name}; }
sub bvm { my ($self)=@_; return $self->{bvm}; }
sub utc_rd_values {
my ($self)=@_;
return (
Date_to_Days($self->{year}, $self->{month}, $self->{day})-1,
0,
0,
);
}
sub from_object {
my ($class, $object)=@_;
my ($days, $secs, $nanosecs) = $object->utc_rd_values();
my ($y, $m, $d, $hour, $min, $seconds) =
Add_Delta_DHMS(1, 1, 1, 0, 0, 0, $days-1, 0, 0, $secs);
return $class->new(
day => $d,
month => $m,
year => $y,
hour => $hour,
minute => $min,
seconds => $seconds,
nanosecond => $nanosecs,
);
}
1;
__END__
=head1 NAME
DateTime::Calendar::Liturgical::Christian - calendar of the church year
=head1 SYNOPSIS
$dtclc = DateTime::Calendar::Liturgical::Christian->new(
day=>4,
month=>6,
year=>2006);
print $dtclc->name(); # 'Pentecost'
print $dtclc->colour(); # 'red'
=head1 DESCRIPTION
This module will return the name, season, week number and liturgical colour
for any day in the Gregorian calendar. It will eventually support the
liturgical calendars of several churches (hopefully at least Anglican,
Lutheran, Orthodox and Roman Catholic). At present it only knows the calendar
for the Episcopal Church of the USA.
If you find bugs, or if you have information on the calendar of another
liturgical church, please do let me know (thomas at thurman dot org dot uk).
=head1 OVERVIEW
Some churches use a special church calendar. Days and seasons within the year
may be either "fasts" (solemn times) or "feasts" (joyful times). The year is
structured around the greatest feast in the calendar, the festival of the
Resurrection of Jesus, known as Easter, and the second greatest feast, the
festival of the Nativity of Jesus, known as Christmas. Before Christmas and
Easter there are solemn fast seasons known as Advent and Lent respectively.
After Christmas comes the feast of Epiphany, and after Easter comes the feast
of Pentecost. These days have the adjacent seasons named after them.
The church's new year falls on Advent Sunday, which occurs around the start of
December. Then follows the four-week fast season of Advent, then comes the
Christmas season, which lasts twelve days; then comes Epiphany, then the
forty days of Lent. Then comes Easter, then the long season of Pentecost
(which some churches call Trinity, after the feast which falls soon after
Pentecost). Then the next year begins and we return to Advent again.
Along with all these, the church remembers the women and men who have made
a positive difference in church history by designating feast days for them,
usually on the anniversary of their death. For example, we remember St. Andrew
on the 30th day of November in the Western churches. Every Sunday is the feast
day of Jesus, and if it has no other name is numbered according to the
season in which it falls. So, for example, the third Sunday in Pentecost
season would be called Pentecost 3.
Seasons are traditionally assigned colours, which are used for clothing and
other materials. The major feasts are coloured white or gold. Fasts are
purple. Feasts for martyrs (people who died for their faith) are red.
Other days are green.
=head1 CONSTRUCTOR
=over 4
=item new ([ OPTIONS ])
This constructs a DateTime::Calendar::Liturgical::Christian object. It takes
a series of named options. Possible options are:
B<year> (required). The year AD in the Gregorian calendar.
B<month> (required). The month number in the Gregorian calendar. 1 is January.
B<day> (required). The day of the month.
B<tradition> (recommended). The tradition to use. Currently only C<ECUSA> is known.
B<advent_blue>. It is currently popular in ECUSA to colour Advent blue,
instead of purple, which will happen if this option is set to 1.
B<bvm_blue>. Some people mark feasts of the Blessed Virgin Mary, the mother of
Jesus, with blue instead of white. This will happen if this option is set to
1. To tell the difference between this blue and C<advent_blue>'s blue, see the
C<bvm> method, below.
B<rose>. Some people colour the middle Sundays of Lent and Advent pink, or
"rose", instead of purple. This will happen if this option is set to 1.
=item from_object ( OBJECT )
Constructs a DateTime::Calendar::Liturgical::Christian object from an object
of any other DateTime class.
=back
=head1 METHODS
=over 4
=item name
Returns the name of the feast, if any.
=item season
Returns the season.
=item colour
Returns the colour of the day. Can be C<red>, C<green>, C<white>, or C<purple>,
or C<blue> or C<rose> if the relevant options are set.
=item color
Alternative spelling of C<colour>.
=item bvm
Returns true if the current day is a feast of the Blessed Virgin Mary. This
can be used to distinguish Advent blue from Marian blue.
=item day
Returns the day number which was used to construct the object.
=item month
Returns the month number which was used to construct the object.
=item year
Returns the year number which was used to construct the object.
( run in 1.781 second using v1.01-cache-2.11-cpan-a49fcb8fa48 )