自定义日历控件
背景:在开放一款嵌入式软件时涉及到数据操作需要按照日期来查询的,QT内置控件不好点,用户操作起来体验很差,所以写了这个自定义日历控件
说明:单击上下按钮切换当前数字,年月日已绑定变化,根据每年每月有多少天设定对应可选择的设置范围,可以回到今天的日期
控件展示:
补充:我相信正常人一看都就会操作,需要注意的是,选择完日期后点击确认按钮才能获取选择的日期,并且窗口会隐藏
完整代码(由于不想使用ui文件导致代码看起来有点多)
class myCalendar : public QWidget
{
Q_OBJECT
public:
myCalendar(QWidget *parent = 0);
~myCalendar();
public:
void initWidget();
QDate getCurrentDate(); // 获取当前选择的日期
int manyDayInOneMonth(); // 计算当前月份中的天数
signals:
void SigOkBtnClicked();
private:
QPushButton *m_btnGruop[11];
};
myCalendar::myCalendar(QWidget *parent)
: QWidget(parent)
{
for(int i = 0;i<11;++i)
{
m_btnGruop[i]= NULL;
}
initWidget();
}
myCalendar::~myCalendar()
{
for(int i = 0;i<11;++i)
{
if(m_btnGruop[i])
{
delete m_btnGruop[i];
m_btnGruop[i]=NULL;
}
}
}
void myCalendar::initWidget()
{
QGridLayout*grid = new QGridLayout();
for(int i = 0;i<3;++i)
{
for(int j = 0;j<3;++j)
{
m_btnGruop[i*3+j] = new QPushButton();
m_btnGruop[i*3+j]->setSizePolicy(QSizePolicy::Preferred,QSizePolicy::Preferred);
m_btnGruop[i*3+j]->setFocusPolicy(Qt::NoFocus);
grid->addWidget(m_btnGruop[i*3+j],i,j);
}
}
QVBoxLayout*lay1 = new QVBoxLayout();
for(int j =9;j<11;++j)
{
m_btnGruop[j]=new QPushButton();
m_btnGruop[j]->setSizePolicy(QSizePolicy::Preferred,QSizePolicy::Preferred);
m_btnGruop[j]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[j]->setFocusPolicy(Qt::NoFocus);
lay1->addWidget(m_btnGruop[j]);
}
m_btnGruop[9]->setText("回到今天");
connect(m_btnGruop[9],&QPushButton::clicked,[=](){
QDate date = QDate::currentDate();
QString curDate = date.toString("yyyy-MM-dd");
m_btnGruop[3]->setText(curDate.left(4));
m_btnGruop[4]->setText(curDate.mid(5,2));
m_btnGruop[5]->setText(curDate.right(2));
});
m_btnGruop[10]->setText("确认");
connect(m_btnGruop[10],&QPushButton::clicked,[=](){
emit SigOkBtnClicked();
// this->hide();
});
lay1->setStretch(0,1);
lay1->setStretch(1,1);
lay1->setSpacing(1);
QHBoxLayout*lay2 = new QHBoxLayout();
lay2->addLayout(grid);
lay2->addLayout(lay1);
lay2->setStretch(0,3);
lay2->setStretch(1,1);
lay2->setSpacing(1);
QDate date = QDate::currentDate();
QString curDate = date.toString("yyyy-MM-dd");
m_btnGruop[0]->setText("上一年");
m_btnGruop[0]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[4]->setText(curDate.mid(5,2));
m_btnGruop[1]->setText("上一月");
m_btnGruop[1]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[2]->setText("上一天");
m_btnGruop[2]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[3]->setText(curDate.left(4));
m_btnGruop[3]->setStyleSheet("background-color:black;color:cyan;font-size:40px;");
m_btnGruop[4]->setStyleSheet("background-color:black;color:green;font-size:40px;");
m_btnGruop[5]->setText(curDate.right(2));
m_btnGruop[5]->setStyleSheet("background-color:black;color:red;font-size:40px;");
m_btnGruop[6]->setText("下一年");
m_btnGruop[6]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[7]->setText("下一月");
m_btnGruop[7]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[8]->setText("下一天");
m_btnGruop[8]->setStyleSheet("QPushButton{background-color:black;color:white;font-size:20px;}QPushButton:pressed{color:blue;background-color: rgb(245, 121, 0);border: 1px solid rgb(12 , 138 , 235);padding-left:5px;padding-top:5px;}");
m_btnGruop[3]->setEnabled(false);
m_btnGruop[4]->setEnabled(false);
m_btnGruop[5]->setEnabled(false);
connect(m_btnGruop[0],&QPushButton::clicked,[=](){
int num = m_btnGruop[3]->text().toInt();
num--;
m_btnGruop[3]->setText(QString::number(num));
int day =manyDayInOneMonth();
if(m_btnGruop[5]->text().toInt()>day)
{
m_btnGruop[5]->setText(QString::number(day));
}
});
connect(m_btnGruop[6],&QPushButton::clicked,[=](){
int num = m_btnGruop[3]->text().toInt();
num++;
m_btnGruop[3]->setText(QString::number(num));
int day =manyDayInOneMonth();
if(m_btnGruop[5]->text().toInt()>day)
{
m_btnGruop[5]->setText(QString::number(day));
}
});
connect(m_btnGruop[1],&QPushButton::clicked,[=](){
int num = m_btnGruop[4]->text().toInt();
num--;
if(num>=0&&num<=12)
{
if(num == 0)
{
m_btnGruop[4]->setText("12");
int tmp = m_btnGruop[3]->text().toInt();
m_btnGruop[3]->setText(QString::number(tmp-1));
}
else{
m_btnGruop[4]->setText(QString::number(num));
}
int day =manyDayInOneMonth();
if(m_btnGruop[5]->text().toInt()>day)
{
m_btnGruop[5]->setText(QString::number(day));
}
}
});
connect(m_btnGruop[7],&QPushButton::clicked,[=](){
int num = m_btnGruop[4]->text().toInt();
num++;
if(num>=1&&num<=13)
{
if(num == 13)
{
m_btnGruop[4]->setText("1");
int tmp = m_btnGruop[3]->text().toInt();
m_btnGruop[3]->setText(QString::number(tmp+1));
}
else
{
m_btnGruop[4]->setText(QString::number(num));
}
int day =manyDayInOneMonth();
if(m_btnGruop[5]->text().toInt()>day)
{
m_btnGruop[5]->setText(QString::number(day));
}
}
});
connect(m_btnGruop[2],&QPushButton::clicked,[=](){
int num = m_btnGruop[5]->text().toInt();
num--;
int day = manyDayInOneMonth();
if(num>=0&&num<=day)
{
if(num == 0)
{
int tmp =m_btnGruop[4]->text().toInt();
if(tmp>1)
{
m_btnGruop[4]->setText(QString::number(tmp-1));
}
else if(tmp == 1)
{
m_btnGruop[4]->setText("12");
tmp = m_btnGruop[3]->text().toInt();
m_btnGruop[3]->setText(QString::number(tmp-1));
}
day = manyDayInOneMonth();
m_btnGruop[5]->setText(QString::number(day));
}
else
{
m_btnGruop[5]->setText(QString::number(num));
}
}
});
connect(m_btnGruop[8],&QPushButton::clicked,[=](){
int num = m_btnGruop[5]->text().toInt();
num++;
int day = manyDayInOneMonth();
if(num>=1&&num<=day+1)
{
if(num<=day)
{
m_btnGruop[5]->setText(QString::number(num));
}
else if(num == day+1)
{
m_btnGruop[5]->setText("1");
int tmp =m_btnGruop[4]->text().toInt();
if(tmp<12)
{
m_btnGruop[4]->setText(QString::number(tmp+1));
}
else if(tmp ==12)
{
m_btnGruop[4]->setText("1");
tmp = m_btnGruop[3]->text().toInt();
m_btnGruop[3]->setText(QString::number(tmp+1));
}
}
}
});
grid->setSpacing(0);
grid->setVerticalSpacing(1);
grid->setColumnStretch(0,1);
grid->setColumnStretch(1,1);
grid->setColumnStretch(2,1);
grid->setRowStretch(0,1);
grid->setRowStretch(1,1);
grid->setRowStretch(2,1);
grid->setContentsMargins(2,2,2,2);
lay2->setContentsMargins(6,6,6,6);
this->setLayout(lay2);
}
// 计算当前月中有多少天
int myCalendar::manyDayInOneMonth()
{
if(!m_btnGruop[3]||!m_btnGruop[4]||!m_btnGruop[5])
{
return 0;
}
int year = m_btnGruop[3]->text().toInt();
int month = m_btnGruop[4]->text().toInt();
int maxDay = 30;
if(month == 2)
{
bool isLoopYear = (((0 == (year % 4)) && (0 != (year % 100))) || (0 == (year % 400)));
if (isLoopYear)
{
maxDay = 29;
}
else
{
maxDay = 28;
}
}
else if(month == 1 || month == 3 || month == 5 || month == 7 || month == 8 || month == 10 || month == 12)
{
maxDay =31;
}
return maxDay;
}
QDate myCalendar::getCurrentDate()
{
QDate date = QDate::currentDate();
if(!m_btnGruop[3]||!m_btnGruop[4]||!m_btnGruop[5])
{
return date;
}
QString curDate=m_btnGruop[3]->text();
curDate+="/";
curDate+=m_btnGruop[4]->text();
curDate+="/";
curDate+=m_btnGruop[5]->text();
date = QDate::fromString(curDate,"yyyy/M/d");
return date;
}