0
点赞
收藏
分享

微信扫一扫

C++ win32控制台显示月历

IT影子 2023-01-12 阅读 66


事情的起因是前端同事一时性♂起想自己写一个日历控件

然后研究了一下逻辑思路


我们参考一下win10系统的显示格式

C++   win32控制台显示月历_i++



从日期数据来说,这是一个6X7的矩阵

除了当月的天数以外,头尾还要补齐上月末与下月初的日期。



首先,需要确定本月显示的天数,那么第一件事,得判断当前月共有多少天,包括闰年的处理


int getdays(int year,int month)
{

switch(month)
{
case 12: return 31;
case 11: return 30;
case 10: return 31;
case 9: return 30;
case 8: return 31;
case 7: return 31;
case 6: return 30;
case 5: return 31;
case 4: return 30;
case 3: return 31;
case 2: if((year%400==0)||(year%4==0)&&(year%100!=0))
return 29;
else
return 28;
case 1: return 31;
case 0: return 31;
}


}



注意,这里加了一个case 0,因为下文中会引用到求上月份天数,如果是1月份的上个月,即传入0,那么实际返回的应是去年的12月所以是31天。


确定好本月以后,我们推一下上个月需要的天数,首先就要确定本月的一号在矩阵的位置,也就是周几。拿上图为例,其排列是周一至周日。

那么如果是周日(7),则需要补上6天,即,需要补的天数为当前月1号的星期-1

那么求当前月1号的星期也可以通过本日的日期信息获取(week-(day-1)%7)这个应该不难理解,即计算日期的差值,如果求出的值小于1那么就再加上7


这样我们就能求出开始需要补充的天数了。


后面追加的天数更为简单,直接初始成1号往后加就好了


大体思路确定了以后,我们开始过一遍这个6*7矩阵


首先是头部分,我用一个自减变量来标记他,这样做的好处是,我可以直接用上个月的天数减去这个变量求得应该显示的日期,比如说我本月的1号是在周日

那么就需要补充上月的6天,我第一个显示的就是31(上个月天数)-(6-1)即26号,最后显示31-0=31号


if(needday-->0)
{
time_table[i][j]=Pdays-needday;
printf("%02d%c",time_table[i][j],j==6?'\n':' ');
}


然后是本月的正常日期,也可以加上后面追加的一起算,只要把超过当前天数时,天数清空就好了。即:

time_table[i][j]=day_count++;  
if(day_count>days)
{
day_count=1;
}
printf("%02d%c",time_table[i][j],j==6?'\n':' ');



下面贴出完整代码:

#include<stdio.h>
#include<time.h>
#include<stdlib.h>
#include<windows.h>
#include<string.h>
using namespace std;
int i,j;

int time_table[6][7];

int getdays(int year,int month)
{


switch(month)
{
case 12: return 31;
case 11: return 30;
case 10: return 31;
case 9: return 30;
case 8: return 31;
case 7: return 31;
case 6: return 30;
case 5: return 31;
case 4: return 30;
case 3: return 31;
case 2: if((year%400==0)||(year%4==0)&&(year%100!=0))
return 29;
else
return 28;
case 1: return 31;
case 0: return 31;
}


}




int main()
{
SYSTEMTIME sys;
GetLocalTime( &sys );
HANDLE consolehwnd;
consolehwnd=GetStdHandle(STD_OUTPUT_HANDLE);
/*
printf("%d\n",sys.wYear);
printf("%d\n",sys.wMonth);
printf("%d\n",sys.wDay);
printf("%d\n",sys.wDayOfWeek);
printf("%d\n",sys.wHour);
printf("%d\n",sys.wMinute);
printf("%d\n",sys.wSecond);
printf("%d\n",sys.wMilliseconds);
*/

int days=getdays(sys.wYear,sys.wMonth);

int Pdays=getdays(sys.wYear,sys.wMonth-1);
// printf("%d\n",days);

int day_count=1;

int FirstDayWeekAsMonth=sys.wDayOfWeek-(sys.wDay-1)%7;
if(FirstDayWeekAsMonth<1)
FirstDayWeekAsMonth+=7;

// printf("%d\n", FirstDayWeekAsMonth);

int needday=FirstDayWeekAsMonth-1;
printf("%s\n", "一 二 三 四 五 六 日");
SetConsoleTextAttribute(consolehwnd,FOREGROUND_INTENSITY|FOREGROUND_GREEN);
for(i=0;i<6;i++)
for(j=0;j<7;j++)
{
if(needday-->0)
{
time_table[i][j]=Pdays-needday;
SetConsoleTextAttribute(consolehwnd,FOREGROUND_RED);
printf("%02d%c",time_table[i][j],j==6?'\n':' ');
SetConsoleTextAttribute(consolehwnd,FOREGROUND_INTENSITY|FOREGROUND_GREEN);
}
else
{
time_table[i][j]=day_count++;
printf("%02d%c",time_table[i][j],j==6?'\n':' ');
if(day_count>days)
{
day_count=1;
SetConsoleTextAttribute(consolehwnd,FOREGROUND_INTENSITY|FOREGROUND_BLUE);
}

}
}
SetConsoleTextAttribute(consolehwnd, FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE);

// for(i=0;i<6;i++)
// for(j=0;j<7;j++)
// printf("%02d%c",time_table[i][j],j==6?'\n':' ');

return 0;
}





运行截图

注:GetLocalTime实现获取当前日期信息,SetConsoleTextAttribute实现改变控制台输出颜色,为了区别月份

C++   win32控制台显示月历_i++_02










举报

相关推荐

0 条评论