前言
在当今数字化的时代,通讯录作为管理联系人信息的重要工具,在我们的生活和工作中扮演着不可或缺的角色。从早期简单的纸质通讯录,到如今功能丰富的电子通讯录应用,其发展历程见证了科技的不断进步。对于编程爱好者和开发者来说,亲手打造一个属于自己的通讯录程序,不仅能深入理解数据结构和算法的应用,还能锻炼解决实际问题的能力。
C 语言作为一种广泛应用且高效的编程语言,以其强大的底层操作能力和良好的移植性,成为开发此类程序的理想选择。今天,我们就来详细剖析一个基于 C 语言的图形化通讯录程序。该程序借助了 easyx 图形库,为用户提供了直观的操作界面,同时运用了链表这种数据结构来存储和管理联系人信息。通过对这个程序的学习和分析,我们可以了解到如何在 C 语言中实现数据的增删改查操作,以及如何将图形化界面与数据处理逻辑相结合。无论是对于初学者掌握 C 语言的基本语法和编程技巧,还是对于有一定经验的开发者探索更高效的程序设计方法,都具有很大的参考价值。接下来,让我们深入代码,一探究竟。
环境准备
1.推荐vs2022,只要能运行c程序的ide都是可行的。
2.在easyx的官网下载easyx,其会自动给你配置图形库。为图形化界面做准备。
此外,通讯录源码的文章很多,但是很多都不是图形化界面,或者使用了的是qt,我这篇文章为读者开辟了一条新的实现路径,界面的样式没有做很好的图形展示,主打一个先实现功能,这个源码主要是为读者提供一个思路,起到抛砖引玉的作用足以,至于界面的美化,读者也可自己进行尝试。
程序核心功能解析
- 联系人信息管理:程序定义了
Contact
结构体来存储联系人的详细信息,包括姓名、电话、邮箱和类别等。同时,使用链表结构来组织这些联系人信息,使得数据的添加、删除和修改操作更加灵活高效。 - 图形化界面:借助 easyx 图形库,程序创建了一个简单直观的图形界面,用户可以通过菜单选择不同的操作,如添加联系人、查询联系人等。这种图形化的交互方式提高了用户体验,使得程序更加易用。
- 数据持久化:程序实现了数据的保存和加载功能,能够将联系人信息存储到文件中,以便下次使用时能够快速恢复数据。这一功能保证了数据的安全性和持续性。
#include <graphics.h>
#include <wchar.h>
#define MAX_LEN 100
#define BUTTON_WIDTH 200
#define BUTTON_HEIGHT 40
#define WINDOW_WIDTH 640
#define WINDOW_HEIGHT 480
// 联系人类型枚举
typedef enum {
OFFICE = 0, // 办公类
PERSONAL, // 个人类
BUSINESS // 商务类
} ContactType;
// 更新联系人结构体
typedef struct Contact {
wchar_t name[MAX_LEN]; // 姓名
wchar_t phone[MAX_LEN]; // 电话号码
wchar_t email[MAX_LEN]; // 电邮地址
ContactType type; // 联系人类别
struct Contact* next; // 指向下一个联系人
} Contact;
// EasyTextBox:用户输入文本框控件
class EasyTextBox {
private:
int left = 0, top = 0, right = 0, bottom = 0; // 控件坐标
wchar_t* text = NULL; // 控件内容
size_t maxlen = 0; // 文本框最大内容长度
wchar_t* label = NULL; // 标签文字
public:
// 创建文本框并显示标签
void Create(int x1, int y1, int x2, int y2, int max, const wchar_t* labelText) {
maxlen = max;
text = new wchar_t[maxlen];
text[0] = 0;
left = x1, top = y1, right = x2, bottom = y2;
label = new wchar_t[wcslen(labelText) + 1];
wcscpy_s(label, wcslen(labelText) + 1, labelText);
Show(); // 显示文本框和标签
}
~EasyTextBox() {
if (text != NULL) delete[] text;
if (label != NULL) delete[] label;
}
wchar_t* Text() {
return text;
}
// 检查鼠标点击是否在文本框区域内
bool Check(int x, int y) {
return (left <= x && x <= right && top <= y && y <= bottom);
}
// 显示文本框,并在文本框前显示标签
void Show() {
int oldlinecolor = getlinecolor();
int oldbkcolor = getbkcolor();
int oldfillcolor = getfillcolor();
setlinecolor(LIGHTGRAY);
setbkcolor(0xeeeeee);
setfillcolor(0xeeeeee);
fillrectangle(left, top, right, bottom);
// 显示标签文本
outtextxy(left - textwidth(label) - 10, top + (bottom - top - textheight(label)) / 2, label);
// 显示文本框中的内容
outtextxy(left + 10, top + 5, text);
setlinecolor(oldlinecolor);
setbkcolor(oldbkcolor);
setfillcolor(oldfillcolor);
}
// 处理文本框输入事件
void OnMessage() {
// 绘制文本框并等待输入
int oldlinecolor = getlinecolor();
int oldbkcolor = getbkcolor();
int oldfillcolor = getfillcolor();
setlinecolor(BLACK);
setbkcolor(WHITE);
setfillcolor(WHITE);
fillrectangle(left, top, right, bottom);
outtextxy(left + 10, top + 5, text);
int width = textwidth(text);
int counter = 0; // 光标闪烁计数器
bool binput = true; // 是否继续输入
ExMessage msg;
while (binput) {
while (binput && peekmessage(&msg, EX_MOUSE | EX_CHAR, false)) {
if (msg.message == WM_LBUTTONDOWN)