软件部分能够实现对老师的添加,老师可以对学生进行添加,删除,修改,查看。同时也能添加和删除相关课程,查询每门课学生人数,出勤情况,同时也能及时查看学生刷卡情况,能够看到学生照片用以对比学生信息。
系统模型设计过程如下,老师可以通过对上位机的操作,完成相关课程的开课,以及选择相关学生,学生通过刷卡完成上课考勤,老师通过对相关信息的筛选完成学生上课信息的查看,相关模型图如图1所示。
系统采用STC公司IAP15W4K58S4单片机作为主控制芯片、采用ESP8266作为WIFI通信模块、RFID-RC522为读卡器的标签、1602液晶显示模块,此外还需解决电源供电模块间工作电压不一致等问题,USB转TTL串口以及按键,LED提示等电路设计,系统的结构如图2所示。
图2 系统硬件结构图
初始化包括初始化单片机,液晶屏以及RFID,过程中系统液晶屏会显示“RFID System”在完成初始化后则显示“connect server..”。初始化程序如下:
init_system(); //初始化系统单片机
init_lcd(); //初始化液晶屏,并清屏
fill_screen();
sprintf(lcd_line1,"RFID System");
write_string(lcd_line1,1,1);
sprintf(lcd_line2,"connect server..");
write_string(lcd_line2,2,1);
init_rfid_system(); //初始化RFID
WDT_CONTR = 0x37; //开启看门狗
看门狗的功能是为了防止程序非正常工作时,从新回到系统上电状态,在程序调试和运行过程都有着很重要的意义。
完成相关初始化后,即调用加入wifi程序,需要对此进行判断,是否加入成功,若加入成功,即可继续操作,若没有成功,则继续加入wifi的程序。相关代码如下:
if (setup_wifi_dev()) {
Serial_println("wifi device ok!");
wifi_dev_ok= 1;
LED1= 0; //网络连接成功,LED1亮
fill_screen();
sprintf(lcd_line1,"RFID System");
write_string(lcd_line1,1,1);
sprintf(lcd_line2,"Ready!");
write_string(lcd_line2,2,1);
}else {
Serial_println("wifi device error!");
while(1) {
DelayMS(5000); //延时5秒,重启设备
return;
}
}
成功加入WIFI后,进行清屏等相关操作,然后进入死循环,执行读卡,向服务器发送数据等操作,为了防止长时间不用而产生的掉线,做了一个网络心跳操作,即定期向服务器发送不相干的操作保证网络连接相关程序如下:
while (1) {
WDT_CONTR = 0x37; //开启看门狗
process_rfid_event(); //RFID系统扫描卡片
if (time0_flag == 1) {
fill_screen();
sprintf(lcd_line1,"RFID System");
write_string(lcd_line1,1,1);
sprintf(lcd_line2,"Ready!");
write_string(lcd_line2,2,1);
time0_flag = 0;
LED2 = ~LED2; //状态指示灯 闪烁
if (send_heartbeat_time_interval_action--<= 0) { //定期发送网络心跳包给服务器
send_heartbeat_time_interval_action= send_heartbeat_time_interval; //设置计数初值
if(send_heartbeat_data_to_server() == 0) { //发送数据异常,重启系统
goto START;
}
}
}
if(recv_valid_data) { //判断标志位 是否接收到网络数据
if (g_i < 32) //判断wifi是否有 有效数据
continue;
recv_valid_data = 0;
Serial_println(g_Rec_Buf);
if (Hand("+IPD,")) { //接收到有效数据
parse_buf(); //处理接收到的网络数据
}
if (Hand("CLOSED")) { //接收到客户端断开信息
CLR_Buf();
LED2 = 1; //灭 第2个指示灯
g_connect_online= 0;
Serial_println("devdisconnect");
gotoSTART;
}
}
本设计是针对高校学生考勤,所以它的数据量不是特别的大,在设计时考虑到低成本、高性能的特点决定使用MYSQL数据库,同时针对系统的工作原理,对数据库进行了优化设计。
在数据库的概念设计中,我们通常用E-R图来表示实体与实体属性和实体之间的关系,通过E-R图来描述现实世界的实体,这样即使不了解系统设计的人也能理解数据库设计。本系统的数据库一共设计了6张数据库表,数据库名为rfidsys。
1.teacher(教师表):该表用于存储系统教师的信息以及登录账号和密码。内容如下面信息表4-1所示。
表4-1 teacher
序号 |
名称 |
别名 |
类型 |
长度 |
主外键 |
1 |
idteacher |
教师编号 |
INT |
11 |
Primary key |
2 |
name |
教师姓名 |
Varchar |
45 |
|
3 |
sex |
教师性别 |
Varchar |
2 |
|
4 |
username |
登录名 |
Varchar |
45 |
|
5 |
passwd |
密码 |
Varchar |
45 |
|
6 |
age |
年龄 |
INT |
11 |
|
2.studentinfo(学生信息表):该表用于存储系统的学生信息,内容如下面信息表4-2所示。
表4-2 studentinfo
序号 |
名称 |
别名 |
类型 |
长度 |
主外键 |
1 |
idstudentinfo |
学生编号 |
Int |
11 |
Primar key |
2 |
name |
姓名 |
Varchar |
45 |
|
3 |
no |
学号 |
Int |
45 |
|
4 |
rfidno |
校园卡号 |
Varchar |
45 |
|
5 |
sex |
性别 |
Varchar |
2 |
|
6 |
ago |
年龄 |
Varchar |
11 |
|
7 |
class |
班级 |
Varchar |
45 |
|
8 |
py |
姓名拼音 |
Varchar |
45 |
|
3.classinfo(班级信息表):该表用于存班级信息,如表4-3所示。
表4-3 classinfo
序号 |
名称 |
别名 |
类型 |
长度 |
主外键 |
1 |
idclassinfo |
班级编号 |
int |
11 |
Primar key |
2 |
name |
班级名 |
Varchar |
45 |
|
3 |
classnum |
教室号 |
int |
11 |
|
4.teacherlesson (老师上课表):用于存储老师上课情况,如表4-4所示。
表4-4 teacherlesson
序号 |
名称 |
别名 |
类型 |
长度 |
主外键 |
1 |
id teacherlesson |
id号 |
Int |
11 |
Primar key |
2 |
teacherid |
教师编号 |
Int |
11 |
Foreign key |
3 |
classid |
班级号 |
INT |
11 |
|
4 |
lessonnum |
课时 |
INT |
11 |
|
5 |
isover |
出勤 |
Int |
11 |
|
6 |
readydt |
准备上课 |
DATATIME |
|
|
7 |
begindt |
开始上课 |
DATATIME |
|
|
8 |
enddt |
结束上课 |
DATATIME |
|
|
5.classsetup(设置上课表):该表用于存储班级设置的信息,如表4-5下面的信息所示。
表4-5 classsetup
序号 |
名称 |
别名 |
类型 |
长度 |
主外键 |
1 |
idclasssetup |
设置id |
Int |
11 |
Primary key |
2 |
teacherid |
教师id |
INT |
11 |
|
3 |
studentid |
学生id |
INT |
11 |
Foreign key |
4 |
classindex |
课时 |
Int |
11 |
|
5 |
studentrecord |
出勤记录 |
INT |
11 |
|
6 |
recorddt |
记录时间 |
DATATIME |
|
|
7 |
lessonindex |
课时 |
INT |
11 |
|
6.addclass(添加班级表):该表用于存储班级信息,如表4-6所示。
表4-6 addclass
序号 |
名称 |
别名 |
类型 |
长度 |
主外键 |
1 |
idaddclass |
id |
Int |
11 |
Primary key |
2 |
classname |
班级名 |
Varchar |
45 |
|
初始化数据库包括设置数据库的用户名,登录密码连接成功后打开数据库,相关代码如下:
public void init_db_system()
{
string connStr ="server=localhost;user=root;database=rfidsys;port=3306;password=123456;";
conn = new MySqlConnection(connStr);
try {
conn.Open();
connected_db = true;
}catch(Exception e) {
connected_db = false;
}
}
查询数据库使用MySqlCommand来查询,关闭数据库使用相关函数 conn.Close();来关闭数据库,登录界面判断用户名代码如下:
string strSQL = "select count(*) fromteacher where name = '" + strName + "' and passwd = '" +strPasswd + "'";
if (publicClass.query_sql_scalar(strSQL) != 1)
{
MessageBox.Show("错误的用户名或者密码?");
return;
}
publicClass.uninit_db_system();
MainForm mainForm = new MainForm();
mainForm.strTeacherUserName = strName;
mainForm.Show();
Hide();