⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 calendar.c

📁 万年历的完整算法:1900~2100 它首先计算出对应阳历月第一天对应是星期几
💻 C
📖 第 1 页 / 共 4 页
字号:
    WORD lunar_calendar_date;
    BYTE templeap;
    BYTE tempsolarday;
    WORD temptotal;
    DATE tempcalendar;
    DATE templunar;

    temptotal= total_day;
    get_lunar_month(solar_calendar,lunar_calendar,lunar_leap_month,total_day);
    lunar_calendar_year=lunar_calendar->year;
    lunar_calendar_month=lunar_calendar->month;
    lunar_calendar_date=lunar_calendar->day;

    /*计算当前阳历日的阴历日 具体到初几*/
    if(0< *lunar_leap_month && *lunar_leap_month<13)
    { 			/*如果是闰月则阴历总天数则根据上下两个月来算	*/
        memcpy(&tempcalendar,&solar_calendar,sizeof(DATE));
        tempsolarday=solar_month_total_day(tempcalendar.year,tempcalendar.month);
        temptotal=temptotal+(WORD)tempsolarday;

        tempcalendar.month ++ ;
        if(tempcalendar.month > 12)
        {
            tempcalendar.year ++;
            if(tempcalendar.year > 199)
                tempcalendar.year = 199;
        }
        get_lunar_month(tempcalendar,&templunar,&templeap,temptotal);    /*获取下一个月一号信息*/
        mc_tpumenus_temp_01=tempsolarday-templunar.day+lunar_calendar_date;
    }
    else/* 如果不是闰月则阴历天数 算法*/
    mc_tpumenus_temp_01 = lunar_month_total_day(lunar_calendar_year,lunar_calendar_month);
    /*
    if(0< *lunar_leap_month && *lunar_leap_month<13)
    mc_tpumenus_temp_01--;*/
    lunar_calendar_date=lunar_calendar_date+solar_calendar.day-1;

    if( lunar_calendar_date > mc_tpumenus_temp_01)
    {

        tempsolarday=solar_month_total_day(solar_calendar.year,solar_calendar.month);
        temptotal=temptotal+(WORD)tempsolarday;

        solar_calendar.month ++ ;
        if(solar_calendar.month > 12)
        {
            solar_calendar.year ++;
            if(solar_calendar.year > 199)
                solar_calendar.year = 199;
        }
        get_lunar_month(solar_calendar,&templunar,&templeap,temptotal);    /*获取下一个月一号信息*/

        if( templunar.month == lunar_calendar_month) /*  */
        {
            /*if(0< templeap && templeap<13 templunar.month == lunar_calendar_month)   如果开始月是润月,然后又进两人一月就不是闰月了 */
            *lunar_leap_month = templeap;
            lunar_calendar_month = templunar.month ;
            lunar_calendar_year = templunar.year;
            lunar_calendar_date = lunar_calendar_date - mc_tpumenus_temp_01;

        }
        else
        {
            lunar_calendar_date=lunar_calendar_date - mc_tpumenus_temp_01;
            lunar_calendar_month++;
            if(0< *lunar_leap_month && *lunar_leap_month<13)  /* 如果开始月是润月,然后又进两个一月就不是闰月了*/
                *lunar_leap_month=0;
            if(lunar_calendar_month>12)
            {
                lunar_calendar_month=1;
                lunar_calendar_year++;
                if(lunar_calendar_year>199)
                    lunar_calendar_year=199;
            }

            /*再判断一次是否一个阳历月跨越两个阴历月,可能如果遇上下跨月是闰月又有可能会有错误  */
            mc_tpumenus_temp_01 = lunar_month_total_day(lunar_calendar_year,lunar_calendar_month);
            if(lunar_calendar_date > mc_tpumenus_temp_01)
            {
                lunar_calendar_date=lunar_calendar_date-mc_tpumenus_temp_01;
                lunar_calendar_month++;

                if(lunar_calendar_month>12)
                {
                    lunar_calendar_month=1;
                    lunar_calendar_year++;
                    if(lunar_calendar_year>199)
                        lunar_calendar_year=199;
                }
            }
        }
    }
    lunar_calendar->year=lunar_calendar_year;
    lunar_calendar->month=lunar_calendar_month;
    lunar_calendar->day=lunar_calendar_date;
}

/***************************************
    说明:函数void Lunar_Format_Year(void)
    根据输入变量gc_lunar_calendar_year(按阴历年算)
    计算出阴历天干地支生肖
******************************************/
BYTE Lunar_Format_Year(BYTE Flunar_year)
{
    BYTE lunar_sheng_xiao;
    WORD temp;

    temp=Flunar_year+1900-4;
    lunar_sheng_xiao=(BYTE)(temp%12); /*阴历生肖*/
    return lunar_sheng_xiao;
}

/*星期坐标*/
/* 11日9一9二9三9四9五9六11*/
void DisplayWeek(void)
{
	BYTE i;
	BYTE buf[2];
	
	for(i = 0 ; i < 7 ; i ++)
	{
		strncpy(buf,calendarText8+i*2,2);
		buf[2] = 0;
		DrawTextLine(FONT12,11+i*21,WEEK_LINE,buf,0xff);
		DrawVertLine( 11+i*21+13,WEEK_LINE,30);
		DrawHorizLine(11+i*21,31,  11+i*21+13);
		DrawHorizLine(11+i*21+1,32,11+i*21+13);
	}	
}

/*显示星期图标 以及可能涉及到的其它固定图案*/
void Calendar_Init(void)
{

//	BYTE i;
    /* 画分割线 */
//	for(i=0;i<6;i++)
//		DrawHorizLine( 1,35+i*18,158);
	
    /*显示星期*/
	DisplayWeek();

    /* 显示年坐标 */
/* 7左2005年右7左05月右7左01日右7*/
// 7+8+36+8+7 = 66
// +8+24+8+7  = 47+66 = 113
// +8+24+8+7 = 47+113 =160    
	DrawImage(6,0,IMAGE_BUTTON_LEFT_START);
  DrawTextLine(FONT12,39,SOLAR_LINE,"年",0xff);
  DrawImage(52,0,IMAGE_BUTTON_RIGHT_START);
    /*显示月*/
  DrawImage(65,0,IMAGE_BUTTON_LEFT_START);
  DrawTextLine(FONT12,86,SOLAR_LINE,"月",0xff);
  DrawImage(98,0,IMAGE_BUTTON_RIGHT_START);
    /*显示日*/
  DrawImage(112,0,IMAGE_BUTTON_LEFT_START);
  DrawTextLine(FONT12,133,SOLAR_LINE,"日",0xff);
  DrawImage(146,0,IMAGE_BUTTON_RIGHT_START);
	DrawRect(1,15,158,144);
}


/* 反色显示当天的日期,主要用于月切换和进入万历表的初始化*/
void Calendar_Day_Invert(BYTE Today,BYTE start_day_of_week)
{
    BYTE X_Start,Y_Start,i;
    i=Today+start_day_of_week-1;
    X_Start=X_START_SCREEN+(i%7)*X_INTERVAL;  /*当天号数加上1号星期几再减1除以7就是当天星期*/
    Y_Start=Y_START_SCREEN+(i/7)*Y_INTERVAL;
    if(Y_Start>SOLAR_END_Y)
        Y_Start=Y_START_SCREEN;
    InvertArea(X_Start,Y_Start,22,Y_INTERVAL-4);    /*X_Start-1,Y_Start-3,X_Start+25,Y_Start+11*/
}

void Display_solar_day(DATE solar_calendar)
{
    BYTE X_Start,Y_Start;
    BYTE buf[2];
    
    X_Start=121;
    Y_Start=SOLAR_LINE;
    itoa(solar_calendar.day,buf);
    if(solar_calendar.day<10)
    {
        DrawTextChar(FONT12,X_Start,Y_Start,'0');
        DrawTextLine(FONT12,X_Start+6,Y_Start,buf,0xff);
    }
    else
        DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
}

void Display_solar_lunar_Calendar(DATE solar_calendar,BYTE Start_Day_Of_Week)
{
    BYTE solar_month_day,lunar_leap_month;
    WORD temptotal;
    BYTE X_Start,Y_Start;
    BYTE i,start_week;
    BYTE buf[60];
    BYTE temday;
    DATE lunar_calendar;


    solar_month_day=solar_month_total_day(solar_calendar.year,solar_calendar.month);  /* 算出阳历月总天数 */

    /*显示年 (4,0) :8X16 */
/* 7左2005年右7左05月右7左01日右7*/
// 7+8+36+8+7 = 66
// +8+24+8+7  = 47+66 = 113
// +8+24+8+7 = 47+113 =160    
    X_Start=15;
    Y_Start=SOLAR_LINE;
    itoa(solar_calendar.year+1900,buf);
    DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
    /*显示月*/
    X_Start=74;
    Y_Start=SOLAR_LINE;
    itoa(solar_calendar.month,buf);
    if(solar_calendar.month<10)
    {
        DrawTextChar(FONT12,X_Start,Y_Start,'0');
        DrawTextLine(FONT12,X_Start+6,Y_Start,buf,0xff);
    }
    else
        DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
		Display_solar_day(solar_calendar);

    /*阳阴历显示*/
    X_Start=X_START_SCREEN+(Start_Day_Of_Week)*X_INTERVAL;
    Y_Start=Y_START_SCREEN;
    ClearArea(X_START_SCREEN-1,Y_START_SCREEN-2,158-X_START_SCREEN,SOLAR_END_Y-Y_START_SCREEN);
    temday = solar_calendar.day;
    solar_calendar.day = 1;
    temptotal=get_solar_day_date(solar_calendar,&start_week);
    for(i=0;i<solar_month_day;i++)
    {
        /*memcpy(buf,&solar_Bmp_Table[i][0],18);*/
      	solar_calendar.day = i+1;
	    get_lunar_day(solar_calendar,&lunar_calendar,&lunar_leap_month,temptotal);
	    DrawImageEx2(X_Start+12,Y_Start,8,16,CALENDAR_OFFSET+(lunar_calendar.day-1)*16,8);
	    itoa(solar_calendar.day,buf);
	    if(i+1<10)
    	{
        	DrawTextLine(FONT12,X_Start+6,Y_Start,buf,0xff);
    	}
    	else
        	DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
        X_Start+=X_INTERVAL;
        if(X_Start>=156)  /*59~157   */
        {
            X_Start=X_START_SCREEN;
            Y_Start+=Y_INTERVAL;
            if(Y_Start>SOLAR_END_Y)
                Y_Start=Y_START_SCREEN;
        }
    }
	solar_calendar.day = temday;
}

/* 显示当天阴历属性  因为其它程序也要用到这个函数所以就设计成屏幕可以移动的形式 */
void Display_lunar_pertain(DATE lunar_calendar,BYTE lunar_leap_month,BYTE startX,BYTE startY)
{
    BYTE X_Start,Y_Start;
    WORD size;
    BYTE sheng_xiao;
    BYTE buf[20];

    /*X_Start=startX;*/ /* 15  */
    X_Start=startX;
    Y_Start=startY + 2;  /* 60 固定不变的 */
    ClearArea(X_Start-8 , Y_Start, 158-(X_Start-8), 16);
    if(0<lunar_leap_month && lunar_leap_month<13)
    {
        X_Start-=8;
        /*显示生肖图片 40x40*/
        size=3;
        sheng_xiao=Lunar_Format_Year(lunar_calendar.year);
        strncpy(buf,calendarText1+sheng_xiao*2,2);
        buf[2]=0;
        DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
        X_Start+=12;
        strncpy(buf,calendarText4,12);
        buf[12] = 0;
        DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
        /*
        GetData(calendarText1+sheng_xiao*2,buf,size);
        buf[2]=0;
        DrawString(X_Start,Y_Start,buf);
        X_Start+=16;

        GetMessage(calendarText4,buf);
        DrawString12x12(X_Start,Y_Start,buf + 2);*/
    }
    else
    {
        /*显示生肖图片 40x40*/
        size=3;
        sheng_xiao=Lunar_Format_Year(lunar_calendar.year);
        strncpy(buf,calendarText1+sheng_xiao*2,2);
        buf[2]=0;
        DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
        X_Start+=12;
        strncpy(buf,calendarText5,10);
        buf[10] = 0;
        DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
        /*
        GetData(calendarText1+sheng_xiao*2,buf,size);
        buf[2]=0;
           DrawString(X_Start,Y_Start,buf);
        X_Start+=16;

        GetMessage(calendarText5,buf);
        DrawString12x12(X_Start,Y_Start,buf + 2);*/
    }

    if(0<lunar_leap_month && lunar_leap_month<13)
        X_Start+=12;

    /*显示阴历 月 */
    X_Start+=36;
    size=20;
    strncpy(buf,calendarText2+lunar_calendar.month*2,2);
    buf[2]=0;
    DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);

    /*显示阴历 日 */
    X_Start+=24;         /* 根据现有的条件算出当前的日期的阴历日期 */
    size=20;
    strncpy(buf,calendarText3+lunar_calendar.day*4,4);
    buf[4]=0;
    DrawTextLine(FONT12,X_Start,Y_Start,buf,0xff);
}

/*反色显示天切换*/
void Calendar_Invert_Day(BYTE old,BYTE now,BYTE start_day_of_week)
{
    BYTE X_Start,Y_Start,i;

    /*显示今天反显区域  (x-1,y-3) (x+25,y+11)*/
    i=old+start_day_of_week-1;
    X_Start=X_START_SCREEN+(i%7)*X_INTERVAL;  /*当天号数加上1号星期几再减1除以7就是当天星期*/
    Y_Start=Y_START_SCREEN+(i/7)*Y_INTERVAL;
    if(Y_Start>SOLAR_END_Y)     /*将超出的行显示到顶上 */
        Y_Start=Y_START_SCREEN;
    InvertArea(X_Start,Y_Start,22,Y_INTERVAL-4); /*X_Start-1,Y_Start-3,X_Start+25,Y_Start+11*/

    /*显示今天反显区域  (x-1,y-3) (x+25,y+11)*/
    i=now+start_day_of_week-1;
    X_Start=X_START_SCREEN+(i%7)*X_INTERVAL;  /*当天号数加上1号星期几再减1除以7就是当天星期*/
    Y_Start=Y_START_SCREEN+(i/7)*Y_INTERVAL;
    if(Y_Start>SOLAR_END_Y)     /*将超出的行显示到顶上 */
        Y_Start=Y_START_SCREEN;
    InvertArea(X_Start,Y_Start,22,Y_INTERVAL-4); /*X_Start-1,Y_Start-3,X_Start+25,Y_Start+11*/
}

/*只是负责显示 实时时钟的值*/
#if 0
BYTE Display_RTC_Time(BYTE X_start,BYTE Y_start,TIME dRTCTime)
{
    BYTE buf[10];

    itoa(dRTCTime.hour,buf);
    if(dRTCTime.hour<10)
    {
        DrawString(X_start,Y_start,"0");
        DrawString(X_start+8,Y_start,buf);
    }
    else
        DrawString(X_start,Y_start,buf);
    X_start+=16;
    DrawString(X_start,Y_start,":");  /*25,40 放到GetKey(0) 的循环中去 */
    X_start+=8;
    itoa(dRTCTime.minute,buf);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -