Is There Any Library or Algorithm for Persian (Shamsi or Jalali) Calendar in Android

Is there any library or algorithm for Persian (Shamsi or Jalali) calendar in Android?

I'm using this algorithm for years and it is very accurate between 1901 and 2099.

Use it and Enjoy! :)

public class Utilities {

private class SolarCalendar {

public String strWeekDay = "";
public String strMonth = "";

int date;
int month;
int year;

public SolarCalendar()
{
Date MiladiDate = new Date();
calcSolarCalendar(MiladiDate);
}

public SolarCalendar(Date MiladiDate)
{
calcSolarCalendar(MiladiDate);
}

private void calcSolarCalendar(Date MiladiDate) {

int ld;

int miladiYear = MiladiDate.getYear() + 1900;
int miladiMonth = MiladiDate.getMonth() + 1;
int miladiDate = MiladiDate.getDate();
int WeekDay = MiladiDate.getDay();

int[] buf1 = new int[12];
int[] buf2 = new int[12];

buf1[0] = 0;
buf1[1] = 31;
buf1[2] = 59;
buf1[3] = 90;
buf1[4] = 120;
buf1[5] = 151;
buf1[6] = 181;
buf1[7] = 212;
buf1[8] = 243;
buf1[9] = 273;
buf1[10] = 304;
buf1[11] = 334;

buf2[0] = 0;
buf2[1] = 31;
buf2[2] = 60;
buf2[3] = 91;
buf2[4] = 121;
buf2[5] = 152;
buf2[6] = 182;
buf2[7] = 213;
buf2[8] = 244;
buf2[9] = 274;
buf2[10] = 305;
buf2[11] = 335;

if ((miladiYear % 4) != 0) {
date = buf1[miladiMonth - 1] + miladiDate;

if (date > 79) {
date = date - 79;
if (date <= 186) {
switch (date % 31) {
case 0:
month = date / 31;
date = 31;
break;
default:
month = (date / 31) + 1;
date = (date % 31);
break;
}
year = miladiYear - 621;
} else {
date = date - 186;

switch (date % 30) {
case 0:
month = (date / 30) + 6;
date = 30;
break;
default:
month = (date / 30) + 7;
date = (date % 30);
break;
}
year = miladiYear - 621;
}
} else {
if ((miladiYear > 1996) && (miladiYear % 4) == 1) {
ld = 11;
} else {
ld = 10;
}
date = date + ld;

switch (date % 30) {
case 0:
month = (date / 30) + 9;
date = 30;
break;
default:
month = (date / 30) + 10;
date = (date % 30);
break;
}
year = miladiYear - 622;
}
} else {
date = buf2[miladiMonth - 1] + miladiDate;

if (miladiYear >= 1996) {
ld = 79;
} else {
ld = 80;
}
if (date > ld) {
date = date - ld;

if (date <= 186) {
switch (date % 31) {
case 0:
month = (date / 31);
date = 31;
break;
default:
month = (date / 31) + 1;
date = (date % 31);
break;
}
year = miladiYear - 621;
} else {
date = date - 186;

switch (date % 30) {
case 0:
month = (date / 30) + 6;
date = 30;
break;
default:
month = (date / 30) + 7;
date = (date % 30);
break;
}
year = miladiYear - 621;
}
}

else {
date = date + 10;

switch (date % 30) {
case 0:
month = (date / 30) + 9;
date = 30;
break;
default:
month = (date / 30) + 10;
date = (date % 30);
break;
}
year = miladiYear - 622;
}

}

switch (month) {
case 1:
strMonth = "فروردين";
break;
case 2:
strMonth = "ارديبهشت";
break;
case 3:
strMonth = "خرداد";
break;
case 4:
strMonth = "تير";
break;
case 5:
strMonth = "مرداد";
break;
case 6:
strMonth = "شهريور";
break;
case 7:
strMonth = "مهر";
break;
case 8:
strMonth = "آبان";
break;
case 9:
strMonth = "آذر";
break;
case 10:
strMonth = "دي";
break;
case 11:
strMonth = "بهمن";
break;
case 12:
strMonth = "اسفند";
break;
}

switch (WeekDay) {

case 0:
strWeekDay = "يکشنبه";
break;
case 1:
strWeekDay = "دوشنبه";
break;
case 2:
strWeekDay = "سه شنبه";
break;
case 3:
strWeekDay = "چهارشنبه";
break;
case 4:
strWeekDay = "پنج شنبه";
break;
case 5:
strWeekDay = "جمعه";
break;
case 6:
strWeekDay = "شنبه";
break;
}

}

}

public static String getCurrentShamsidate() {
Locale loc = new Locale("en_US");
Utilities util = new Utilities();
SolarCalendar sc = util.new SolarCalendar();
return String.valueOf(sc.year) + "/" + String.format(loc, "%02d",
sc.month) + "/" + String.format(loc, "%02d", sc.date);
}
}

Is there any library or algorithm to convert Shamsi(Jalali) to Gregorian date in Java?

import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.Locale;
import java.util.TimeZone;

public class JalaliCalendar extends Calendar {
public static int gregorianDaysInMonth[] = { 31, 28, 31, 30, 31, 30, 31,
31, 30, 31, 30, 31 };
public static int jalaliDaysInMonth[] = { 31, 31, 31, 31, 31, 31, 30, 30,
30, 30, 30, 29 };

public final static int FARVARDIN = 0;
public final static int ORDIBEHESHT = 1;
public final static int KHORDAD = 2;
public final static int TIR = 3;
public final static int MORDAD = 4;
public final static int SHAHRIVAR = 5;
public final static int MEHR = 6;
public final static int ABAN = 7;
public final static int AZAR = 8;
public final static int DEY = 9;
public final static int BAHMAN = 10;
public final static int ESFAND = 11;

private static TimeZone timeZone = TimeZone.getDefault();
private static boolean isTimeSeted = false;

private static final int ONE_SECOND = 1000;
private static final int ONE_MINUTE = 60 * ONE_SECOND;
private static final int ONE_HOUR = 60 * ONE_MINUTE;
private static final long ONE_DAY = 24 * ONE_HOUR;
static final int BCE = 0;
static final int CE = 1;
public static final int AD = 1;
private GregorianCalendar cal;

static final int MIN_VALUES[] = { BCE, 1, FARVARDIN, 1, 0, 1, 1, SATURDAY,
1, AM, 0, 0, 0, 0, 0, -13 * ONE_HOUR, 0 };

static final int LEAST_MAX_VALUES[] = { CE, 292269054, ESFAND, 52, 4, 28,
365, FRIDAY, 4, PM, 11, 23, 59, 59, 999, 14 * ONE_HOUR,
20 * ONE_MINUTE };

static final int MAX_VALUES[] = { CE, 292278994, ESFAND, 53, 6, 31, 366,
FRIDAY, 6, PM, 11, 23, 59, 59, 999, 14 * ONE_HOUR, 2 * ONE_HOUR };

public JalaliCalendar() {
this(TimeZone.getDefault(), Locale.getDefault());
}

public JalaliCalendar(TimeZone zone) {
this(zone, Locale.getDefault());
}

public JalaliCalendar(Locale aLocale) {
this(TimeZone.getDefault(), aLocale);
}

public JalaliCalendar(TimeZone zone, Locale aLocale) {

super(zone, aLocale);
timeZone = zone;
Calendar calendar = Calendar.getInstance(zone, aLocale);

YearMonthDate yearMonthDate = new YearMonthDate(calendar.get(YEAR),
calendar.get(MONTH), calendar.get(DATE));
yearMonthDate = gregorianToJalali(yearMonthDate);
set(yearMonthDate.getYear(), yearMonthDate.getMonth(),
yearMonthDate.getDate());
complete();

}

public Date getGregorianDate(String jalaliDate) {
String[] arr = jalaliDate.split("/");

YearMonthDate jalali = new YearMonthDate(Integer.parseInt(arr[0]),
Integer.parseInt(arr[1]) - 1, Integer.parseInt(arr[2]));

YearMonthDate gDate = jalaliToGregorian(jalali);

Calendar cal = Calendar.getInstance();
cal.clear();
cal.set(gDate.getYear(), gDate.getMonth(), gDate.getDate());

Date dt = cal.getTime();

return dt;
}

public String getJalaliDate(Date gDate) {

Calendar gCal = Calendar.getInstance();

gCal.clear();

gCal.setTime(gDate);
Date dt = gCal.getTime();
int myYear = gCal.get(Calendar.YEAR);
int myMonth = gCal.get(Calendar.MONTH);
int myDay = gCal.get(Calendar.DAY_OF_MONTH);
YearMonthDate gMyDate = new YearMonthDate(myYear, myMonth, myDay);

YearMonthDate jDate = gregorianToJalali(gMyDate);

String jalali = jDate.year + "/" + (jDate.month + 1) + "/" + jDate.date;

return jalali;
}

public JalaliCalendar(int year, int month, int dayOfMonth) {
this(year, month, dayOfMonth, 0, 0, 0, 0);
}

public JalaliCalendar(int year, int month, int dayOfMonth, int hourOfDay,
int minute) {
this(year, month, dayOfMonth, hourOfDay, minute, 0, 0);
}

public JalaliCalendar(int year, int month, int dayOfMonth, int hourOfDay,
int minute, int second) {
this(year, month, dayOfMonth, hourOfDay, minute, second, 0);
}

JalaliCalendar(int year, int month, int dayOfMonth, int hourOfDay,
int minute, int second, int millis) {
super();

this.set(YEAR, year);
this.set(MONTH, month);
this.set(DAY_OF_MONTH, dayOfMonth);

if (hourOfDay >= 12 && hourOfDay <= 23) {

this.set(AM_PM, PM);
this.set(HOUR, hourOfDay - 12);
} else {
this.set(HOUR, hourOfDay);
this.set(AM_PM, AM);
}

this.set(HOUR_OF_DAY, hourOfDay);
this.set(MINUTE, minute);
this.set(SECOND, second);

this.set(MILLISECOND, millis);

YearMonthDate yearMonthDate = jalaliToGregorian(new YearMonthDate(
fields[1], fields[2], fields[5]));
cal = new GregorianCalendar(yearMonthDate.getYear(),
yearMonthDate.getMonth(), yearMonthDate.getDate(), hourOfDay,
minute, second);
time = cal.getTimeInMillis();

isTimeSeted = true;
}

public static YearMonthDate gregorianToJalali(YearMonthDate gregorian) {

if (gregorian.getMonth() > 11 || gregorian.getMonth() < -11) {
throw new IllegalArgumentException();
}
int jalaliYear;
int jalaliMonth;
int jalaliDay;

int gregorianDayNo, jalaliDayNo;
int jalaliNP;
int i;

gregorian.setYear(gregorian.getYear() - 1600);
gregorian.setDate(gregorian.getDate() - 1);

gregorianDayNo = 365 * gregorian.getYear()
+ (int) Math.floor((gregorian.getYear() + 3) / 4)
- (int) Math.floor((gregorian.getYear() + 99) / 100)
+ (int) Math.floor((gregorian.getYear() + 399) / 400);
for (i = 0; i < gregorian.getMonth(); ++i) {
gregorianDayNo += gregorianDaysInMonth[i];
}

if (gregorian.getMonth() > 1
&& ((gregorian.getYear() % 4 == 0 && gregorian.getYear() % 100 != 0) || (gregorian
.getYear() % 400 == 0))) {
++gregorianDayNo;
}

gregorianDayNo += gregorian.getDate();

jalaliDayNo = gregorianDayNo - 79;

jalaliNP = (int) Math.floor(jalaliDayNo / 12053);
jalaliDayNo = jalaliDayNo % 12053;

jalaliYear = 979 + 33 * jalaliNP + 4 * (int) (jalaliDayNo / 1461);
jalaliDayNo = jalaliDayNo % 1461;

if (jalaliDayNo >= 366) {
jalaliYear += (int) Math.floor((jalaliDayNo - 1) / 365);
jalaliDayNo = (jalaliDayNo - 1) % 365;
}

for (i = 0; i < 11 && jalaliDayNo >= jalaliDaysInMonth[i]; ++i) {
jalaliDayNo -= jalaliDaysInMonth[i];
}
jalaliMonth = i;
jalaliDay = jalaliDayNo + 1;

return new YearMonthDate(jalaliYear, jalaliMonth, jalaliDay);
}

public static YearMonthDate jalaliToGregorian(YearMonthDate jalali) {
if (jalali.getMonth() > 11 || jalali.getMonth() < -11) {
throw new IllegalArgumentException();
}

int gregorianYear;
int gregorianMonth;
int gregorianDay;

int gregorianDayNo, jalaliDayNo;
int leap;

int i;
jalali.setYear(jalali.getYear() - 979);
jalali.setDate(jalali.getDate() - 1);

jalaliDayNo = 365 * jalali.getYear() + (int) (jalali.getYear() / 33)
* 8 + (int) Math.floor(((jalali.getYear() % 33) + 3) / 4);
for (i = 0; i < jalali.getMonth(); ++i) {
jalaliDayNo += jalaliDaysInMonth[i];
}

jalaliDayNo += jalali.getDate();

gregorianDayNo = jalaliDayNo + 79;

gregorianYear = 1600 + 400 * (int) Math.floor(gregorianDayNo / 146097); /*
* 146097
* =
* 365
* *
* 400
* +
* 400
* /
* 4
* -
* 400
* /
* 100
* +
* 400
* /
* 400
*/
gregorianDayNo = gregorianDayNo % 146097;

leap = 1;
if (gregorianDayNo >= 36525) /* 36525 = 365*100 + 100/4 */{
gregorianDayNo--;
gregorianYear += 100 * (int) Math.floor(gregorianDayNo / 36524); /*
* 36524
* =
* 365
* *
* 100
* +
* 100
* /
* 4
* -
* 100
* /
* 100
*/
gregorianDayNo = gregorianDayNo % 36524;

if (gregorianDayNo >= 365) {
gregorianDayNo++;
} else {
leap = 0;
}
}

gregorianYear += 4 * (int) Math.floor(gregorianDayNo / 1461); /*
* 1461 =
* 365*4 +
* 4/4
*/
gregorianDayNo = gregorianDayNo % 1461;

if (gregorianDayNo >= 366) {
leap = 0;

gregorianDayNo--;
gregorianYear += (int) Math.floor(gregorianDayNo / 365);
gregorianDayNo = gregorianDayNo % 365;
}

for (i = 0; gregorianDayNo >= gregorianDaysInMonth[i]
+ ((i == 1 && leap == 1) ? i : 0); i++) {
gregorianDayNo -= gregorianDaysInMonth[i]
+ ((i == 1 && leap == 1) ? i : 0);
}
gregorianMonth = i;
gregorianDay = gregorianDayNo + 1;

return new YearMonthDate(gregorianYear, gregorianMonth, gregorianDay);

}

public static int weekOfYear(int dayOfYear, int year) {
switch (dayOfWeek(JalaliCalendar.jalaliToGregorian(new YearMonthDate(
year, 0, 1)))) {
case 2:
dayOfYear++;
break;
case 3:
dayOfYear += 2;
break;
case 4:
dayOfYear += 3;
break;
case 5:
dayOfYear += 4;
break;
case 6:
dayOfYear += 5;
break;
case 7:
dayOfYear--;
break;
}
;
dayOfYear = (int) Math.floor(dayOfYear / 7);
return dayOfYear + 1;
}

public static int dayOfWeek(YearMonthDate yearMonthDate) {

Calendar cal = new GregorianCalendar(yearMonthDate.getYear(),
yearMonthDate.getMonth(), yearMonthDate.getDate());
return cal.get(DAY_OF_WEEK);

}

public static boolean isLeepYear(int year) {
// Algorithm from www.wikipedia.com
if ((year % 33 == 1 || year % 33 == 5 || year % 33 == 9
|| year % 33 == 13 || year % 33 == 17 || year % 33 == 22
|| year % 33 == 26 || year % 33 == 30)) {
return true;
} else
return false;
}

@Override
protected void computeTime() {

if (!isTimeSet && !isTimeSeted) {
Calendar cal = GregorianCalendar.getInstance(timeZone);
if (!isSet(HOUR_OF_DAY)) {
super.set(HOUR_OF_DAY, cal.get(HOUR_OF_DAY));
}
if (!isSet(HOUR)) {
super.set(HOUR, cal.get(HOUR));
}
if (!isSet(MINUTE)) {
super.set(MINUTE, cal.get(MINUTE));
}
if (!isSet(SECOND)) {
super.set(SECOND, cal.get(SECOND));
}
if (!isSet(MILLISECOND)) {
super.set(MILLISECOND, cal.get(MILLISECOND));
}
if (!isSet(ZONE_OFFSET)) {
super.set(ZONE_OFFSET, cal.get(ZONE_OFFSET));
}
if (!isSet(DST_OFFSET)) {
super.set(DST_OFFSET, cal.get(DST_OFFSET));
}
if (!isSet(AM_PM)) {
super.set(AM_PM, cal.get(AM_PM));
}

if (internalGet(HOUR_OF_DAY) >= 12
&& internalGet(HOUR_OF_DAY) <= 23) {
super.set(AM_PM, PM);
super.set(HOUR, internalGet(HOUR_OF_DAY) - 12);
} else {
super.set(HOUR, internalGet(HOUR_OF_DAY));
super.set(AM_PM, AM);
}

YearMonthDate yearMonthDate = jalaliToGregorian(new YearMonthDate(
internalGet(YEAR), internalGet(MONTH),
internalGet(DAY_OF_MONTH)));
cal.set(yearMonthDate.getYear(), yearMonthDate.getMonth(),
yearMonthDate.getDate(), internalGet(HOUR_OF_DAY),
internalGet(MINUTE), internalGet(SECOND));
time = cal.getTimeInMillis();

} else if (!isTimeSet && isTimeSeted) {
if (internalGet(HOUR_OF_DAY) >= 12
&& internalGet(HOUR_OF_DAY) <= 23) {
super.set(AM_PM, PM);
super.set(HOUR, internalGet(HOUR_OF_DAY) - 12);
} else {
super.set(HOUR, internalGet(HOUR_OF_DAY));
super.set(AM_PM, AM);
}
cal = new GregorianCalendar();
super.set(ZONE_OFFSET, timeZone.getRawOffset());
super.set(DST_OFFSET, timeZone.getDSTSavings());
YearMonthDate yearMonthDate = jalaliToGregorian(new YearMonthDate(
internalGet(YEAR), internalGet(MONTH),
internalGet(DAY_OF_MONTH)));
cal.set(yearMonthDate.getYear(), yearMonthDate.getMonth(),
yearMonthDate.getDate(), internalGet(HOUR_OF_DAY),
internalGet(MINUTE), internalGet(SECOND));
time = cal.getTimeInMillis();
}
}

public void set(int field, int value) {
switch (field) {
case DATE: {
super.set(field, 0);
add(field, value);
break;
}
case MONTH: {
if (value > 11) {
super.set(field, 11);
add(field, value - 11);
} else if (value < 0) {
super.set(field, 0);
add(field, value);
} else {
super.set(field, value);
}
break;
}
case DAY_OF_YEAR: {
if (isSet(YEAR) && isSet(MONTH) && isSet(DAY_OF_MONTH)) {
super.set(YEAR, internalGet(YEAR));
super.set(MONTH, 0);
super.set(DATE, 0);
add(field, value);
} else {
super.set(field, value);
}
break;
}
case WEEK_OF_YEAR: {
if (isSet(YEAR) && isSet(MONTH) && isSet(DAY_OF_MONTH)) {
add(field, value - get(WEEK_OF_YEAR));
} else {
super.set(field, value);
}
break;
}
case WEEK_OF_MONTH: {
if (isSet(YEAR) && isSet(MONTH) && isSet(DAY_OF_MONTH)) {
add(field, value - get(WEEK_OF_MONTH));
} else {
super.set(field, value);
}
break;
}
case DAY_OF_WEEK: {
if (isSet(YEAR) && isSet(MONTH) && isSet(DAY_OF_MONTH)) {
add(DAY_OF_WEEK, value % 7 - get(DAY_OF_WEEK));
} else {
super.set(field, value);
}
break;
}
case HOUR_OF_DAY:
case HOUR:
case MINUTE:
case SECOND:
case MILLISECOND:
case ZONE_OFFSET:
case DST_OFFSET: {
if (isSet(YEAR) && isSet(MONTH) && isSet(DATE) && isSet(HOUR)
&& isSet(HOUR_OF_DAY) && isSet(MINUTE) && isSet(SECOND)
&& isSet(MILLISECOND)) {
cal = new GregorianCalendar();
YearMonthDate yearMonthDate = jalaliToGregorian(new YearMonthDate(
internalGet(YEAR), internalGet(MONTH),
internalGet(DATE)));
cal.set(yearMonthDate.getYear(), yearMonthDate.getMonth(),
yearMonthDate.getDate(), internalGet(HOUR_OF_DAY),
internalGet(MINUTE), internalGet(SECOND));
cal.set(field, value);
yearMonthDate = gregorianToJalali(new YearMonthDate(
cal.get(YEAR), cal.get(MONTH), cal.get(DATE)));
super.set(YEAR, yearMonthDate.getYear());
super.set(MONTH, yearMonthDate.getMonth());
super.set(DATE, yearMonthDate.getDate());
super.set(HOUR_OF_DAY, cal.get(HOUR_OF_DAY));
super.set(MINUTE, cal.get(MINUTE));
super.set(SECOND, cal.get(SECOND));

} else {
super.set(field, value);
}
break;
}

default: {
super.set(field, value);
}
}
}

@Override
protected void computeFields() {
boolean temp = isTimeSet;
if (!areFieldsSet) {
setMinimalDaysInFirstWeek(1);
setFirstDayOfWeek(7);

// Day_Of_Year
int dayOfYear = 0;
int index = 0;

while (index < fields[2]) {
dayOfYear += jalaliDaysInMonth[index++];
}
dayOfYear += fields[5];
super.set(DAY_OF_YEAR, dayOfYear);
// ***

// Day_of_Week
super.set(DAY_OF_WEEK,
dayOfWeek(jalaliToGregorian(new YearMonthDate(fields[1],
fields[2], fields[5]))));
// ***

// Day_Of_Week_In_Month
if (0 < fields[5] && fields[5] < 8) {
super.set(DAY_OF_WEEK_IN_MONTH, 1);
}

if (7 < fields[5] && fields[5] < 15) {
super.set(DAY_OF_WEEK_IN_MONTH, 2);
}

if (14 < fields[5] && fields[5] < 22) {
super.set(DAY_OF_WEEK_IN_MONTH, 3);
}

if (21 < fields[5] && fields[5] < 29) {
super.set(DAY_OF_WEEK_IN_MONTH, 4);
}

if (28 < fields[5] && fields[5] < 32) {
super.set(DAY_OF_WEEK_IN_MONTH, 5);
}
// ***

// Week_Of_Year
super.set(WEEK_OF_YEAR, weekOfYear(fields[6], fields[1]));
// ***

// Week_Of_Month
super.set(WEEK_OF_MONTH, weekOfYear(fields[6], fields[1])
- weekOfYear(fields[6] - fields[5], fields[1]) + 1);
//

isTimeSet = temp;
}
}

@Override
public void add(int field, int amount) {

if (field == MONTH) {
amount += get(MONTH);
add(YEAR, amount / 12);
super.set(MONTH, amount % 12);
if (get(DAY_OF_MONTH) > jalaliDaysInMonth[amount % 12]) {
super.set(DAY_OF_MONTH, jalaliDaysInMonth[amount % 12]);
if (get(MONTH) == 11 && isLeepYear(get(YEAR))) {
super.set(DAY_OF_MONTH, 30);
}
}
complete();

} else if (field == YEAR) {

super.set(YEAR, get(YEAR) + amount);
if (get(DAY_OF_MONTH) == 30 && get(MONTH) == 11
&& !isLeepYear(get(YEAR))) {
super.set(DAY_OF_MONTH, 29);
}

complete();
}


Related Topics



Leave a reply



Submit