MFC第七天 单机版数据库增删改的方法和用户登录(密码修改)、权限管理功能的员工管理系统的应用 以及 CCombox类的属性和方法

news2025/2/27 0:38:06

文章目录

  • 员工管理系统的应用
    • 对TCHAR类型简介:
    • Unicode软件开发中的文字转换方式有三种
  • CComboBox控件属性和类库介绍
    • CBS_组合框控件属性
    • CComboBox常用方法
  • 员工管理系统示例代码如下
    • Employer_sql.h
    • Employer_sql.cpp
    • MainDlg.h
    • MainDlg.cpp: 实现文件
    • CLoginDlg.h
    • CLoginDlg.cpp: 实现文件
    • CAdminDlg.h: 实现文件
    • CAdminDlg.cpp: 实现文件
    • CPassDlg.h
    • CPassDlg.cpp: 实现文件

员工管理系统的应用

补充CListCtrl类

1、CListCtrl::GetItemState的调用方法:
Mask 多种状态你要哪一个
a)mask开关:可以同时带入多个开关,返回值再探测是否含有哪个标识。
b)LVIS_FOCUSED 代表 多行列表的焦点项(只有能有一个)
c)LVIS_SELECTED  代表蓝色选中项(可以有多个);
d)CListCtrl::GetSelectionMark是指LVIS_FOCUSED,单一的焦点行所在位置。


#define LVIS_FOCUSED            0x0001
#define LVIS_SELECTED           0x0002
#define LVIS_CUT                0x0004
#define LVIS_DROPHILITED        0x0008
#define LVIS_GLOW               0x0010
#define LVIS_ACTIVATING         0x0020

对TCHAR类型简介:

a)窄字符串:typedef const char* LPCSTR;
b)宽字符串:typedef const wchar_t* LPCWSTR;
c)自适应字符串:typedef TCHAR* LPCTSTR;

#ifdef  UNICODE                     // r_winnt
typedef wchar_t TCHAR;
typedef const wchar_t* LPCTSTR;
#else
typedef char TCHAR;
typedef const char* LPCTSTR;
#endif

全面对项目实施TCHAR类型:

a)从常量上看:
LPCSTR p= “abc”;
LPCWSTR str = “abc”;
ifdef _UNICODE
#define __T(x) L ## x
else
#define __T(x) (x)
b)API:
#ifdef UNICODE
#define SetWindowText SetWindowTextW
#else
#define SetWindowText SetWindowTextA
#endif // !UNICODE

c)C语言库函数
#ifdef UNICODE
#define _tfopen _wfopen
#else
#define _tfopen fopen
#endif
d)C++字符串提供了string和wstring版本,没办法TCHAR版本。
#define _T(x) __T(x)
#define _TEXT(x) __T(x)

Unicode软件开发中的文字转换方式有三种

1、使用sprintf(”%S") 进行转换,不过限制于ASCII码0-127不包括中文

	wchar_t s1[] =L"asdbsadkjq231";  //不含有汉字,纯ASCII码  如何转换为窄的
	char s2[200];

	sprintf(s2, "%s", "bbbb");
	swprintf(s1, L"%s", L"bbbb"); //小写s只能将宽的转为宽, 窄的转为窄的

	sprintf(s2, "%S", s1); //可以通过sprintf(%S);来进行转换 只限制于纯英文格式的 汉字转换不了

2、可以使用CString 来进行转换

#include<atlbase.h>
void Test()
{
	wchar_t s1[] = L"asdbsadkjq231";
	char s2[200] = "abcd";

	//使用W2A A2W T2A T2W A2T W2T时需要前面加上	USES_CONVERSION 包含的头文件#include<atlbase.h>
	//可以实现对宽窄的转换, 适用于中文
	USES_CONVERSION;
	auto p = W2A(s1);
	auto q = A2W(s2);
}

int main()		
{
	Test();
	_CrtDumpMemoryLeaks();//用于检测内存泄露函数
	
	//当CString加上explicit之后不能使用隐式转换,要使用显示的
	//同时CStringT 有部分的转换能力,支持双入口的构造函数,但不支持双出口类型转换。 
	//进来可以时可以是A或者W 出去的时候要是它的原类型,或者使用LPCTSTR

	CString s1 = "萨洛芬妮";
	CString s2 = L"萨洛芬妮";
	CString s3("萨洛芬妮");
	LPCTSTR q = s1;
	LPCWSTR p = s2;
	return 0;
	
	/*关键字explicit主要用于解决隐式类型转换问题。默认情况下,C++编译器会进行一些隐式类型转换,
	例如将一个整数类型变量赋值给一个双精度浮点数类型变量,
	或者将一个自定义类型的对象传递给一个需要该类型对象的函数。
	而使用explicit关键字可以禁止这种隐式的类型转换,只能使用显式类型转换*/

class A
{
public:
	explicit A(int n) {};
	A();
	~A();

private:

};
	A a1 = 2;
	A a2(2);
	A a3 = (A)3;
	fun(3);
	fun(A(3));
	//在上面的示例中,类A的构造函数使用了explicit关键字,
	//因此只有在显式进行类型转换时才能创建对象。对于在函数中传递对象,也必须使用显式类型转换。
}

第三种为使用 _bstr_t 可以双通道的转换

CComboBox控件属性和类库介绍

CBS_组合框控件属性

Box:框 盒子 n.
原始的组合框是一个编辑框和一个ListBox组成,后来变为下拉。
下拉之后分为纯下拉(DropList)和带编辑框的下拉(Dropdown)

/*
 * Combo Box styles
 */
#define CBS_SIMPLE            0x0001L (原始状态的组合框)
#define CBS_DROPDOWN          0x0002L (带编辑框的下拉)
#define CBS_DROPDOWNLIST      0x0003L (不带编辑框的纯下拉)


#define CBS_OWNERDRAWFIXED    0x0010L	自绘下拉(第十章)固定高宽
#define CBS_OWNERDRAWVARIABLE 0x0020L	自绘下拉(第十章)动态高宽
#define CBS_AUTOHSCROLL       0x0040L
#define CBS_OEMCONVERT        0x0080L
#define CBS_SORT              0x0100L		排序的属性(非常不好)
#define CBS_HASSTRINGS        0x0200L
#define CBS_NOINTEGRALHEIGHT  0x0400L
#define CBS_DISABLENOSCROLL   0x0800L
#if(WINVER >= 0x0400)
#define CBS_UPPERCASE         0x2000L		组合框内的编辑框(大写)
#define CBS_LOWERCASE         0x4000L		组合框内的编辑框(小写)
#endif /* WINVER >= 0x0400 */

#endif  /* !NOWINSTYLES */

CComboBox常用方法

class CComboBox : public CWnd
{Edit和ListBox
	DECLARE_DYNAMIC(CComboBox)

// Constructors
public:
	CComboBox();
	virtual BOOL Create(DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID);
	//代码创建下拉控件

	// manipulating listbox items
	int AddString(LPCTSTR lpszString); //加一行
	int DeleteString(UINT nIndex);//删除一行
	int InsertString(_In_ int nIndex, _In_z_ LPCTSTR lpszString); //插入一行
	void ResetContent(); //清空列表
// Attributes
	// for entire combo box
	int GetCount() const; 列表项总数
	int GetCurSel() const; //获取列表当前选中 -1代表没选中
	int SetCurSel(int nSelect); 设置列表当前选中
// Win4
	int GetTopIndex() const; 当大量列表数据,滚动后最上方的索引
	int SetTopIndex(int nIndex); //设置滚动位置
	
	int SetDroppedWidth(UINT nWidth); 设置下拉宽度
	int GetDroppedWidth() const; 获取下拉宽度

	

	// for edit control
	DWORD GetEditSel() const;  获取编辑框内的选中文字,
	BOOL SetEditSel(_In_ int nStartChar, _In_ int nEndChar);  设置 选中
	BOOL LimitText(int nMaxChars);  编辑框的文字长度限制
	
//LB 就是ListBox
	int GetLBText(_In_ int nIndex, _Pre_notnull_ _Post_z_ LPTSTR lpszText) const;//列表第几行的文字
	void GetLBText(int nIndex, CString& rString) const;
	int GetLBTextLen(int nIndex) const;//第几行文字的长度

	// for combobox item
	DWORD_PTR GetItemData(int nIndex) const;//获取每一行的隐藏数据(可能是结构体指针)
	int SetItemData(int nIndex, DWORD_PTR dwItemData);//设置隐藏数据
	void* GetItemDataPtr(int nIndex) const;//对以上函数加强版(指针)
	int SetItemDataPtr(int nIndex, void* pData);/对以上函数加强版(指针)


	int SetItemHeight(int nIndex, UINT cyItemHeight);//设置第几行的行高
	int GetItemHeight(int nIndex) const;
	
	BOOL GetDroppedState() const;

	// for drop-down combo boxes
	void ShowDropDown(BOOL bShowIt = TRUE); //弹出对话框

	int Dir(_In_ UINT attr, _In_ LPCTSTR lpszWildCard);

	// selection helpers
	int FindString(_In_ int nStartAfter, _In_z_ LPCTSTR lpszString) const;
	int SelectString(int nStartAfter, LPCTSTR lpszString);

	// 编辑框内的 Clipboard operations
	void Clear();
	void Copy();
	void Cut();
	void Paste();

// Overridables (must override draw, measure and compare for owner draw)自绘相关
	virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
	virtual void MeasureItem(LPMEASUREITEMSTRUCT lpMeasureItemStruct);
	virtual int CompareItem(LPCOMPAREITEMSTRUCT lpCompareItemStruct);
	virtual void DeleteItem(LPDELETEITEMSTRUCT lpDeleteItemStruct);
};


员工管理系统示例代码如下

对话框中的控件可以进行快速编号的调整使用Ctrl+D快捷键
项目框架如下:
在这里插入图片描述
在这里插入图片描述
账号管理对话框:
在这里插入图片描述
修改密码对话框:
在这里插入图片描述

用户登录对话框:
在这里插入图片描述
主对话框:
在这里插入图片描述

Employer_sql.h

// Employer_sql.h: PROJECT_NAME 应用程序的主头文件
#pragma once
#ifndef __AFXWIN_H__
	#error "在包含此文件之前包含 'pch.h' 以生成 PCH"
#endif
#include "resource.h"		// 主符号

// CApp:	 有关此类的实现,请参阅 Employer_sql.cpp

class CApp : public CWinApp
{
	BOOL ConnectDB(); //数据库的连接
public:
	CApp();
	MYSQL m_sql;
	CString m_sName, m_sPass;
	int m_nPrior{ -1 };
// 重写
public:
	virtual BOOL InitInstance();
	static void DisplayError(CString sSQL); //加上static就不用theApp可以直接通过名称来调用
	DECLARE_MESSAGE_MAP()// 实现
};
extern CApp theApp;

Employer_sql.cpp

// Employer_sql.cpp: 定义应用程序的类行为。
#include "pch.h"
#include "framework.h"
#include "Employer_sql.h"
#include "MainDlg.h"
#include "CLoginDlg.h"
#ifdef _DEBUG
#define new DEBUG_NEW 
#endif

BEGIN_MESSAGE_MAP(CApp, CWinApp)
	ON_COMMAND(ID_HELP, &CWinApp::OnHelp)
END_MESSAGE_MAP()

// CApp 构造
BOOL CApp::ConnectDB()
{
	auto conn = mysql_init(&m_sql);
	if (conn == NULL)
	{
		::MessageBox(nullptr, L"mysql_init", L"提示", 0);
		return FALSE;
	}
	//host参数可以用:"localhost",".","192.168.0.88","127.0.0.1","teacher"
	if (mysql_real_connect(conn, "localhost", "root", "201105", "worker", 3307, NULL, 0) == NULL)
	{
		::MessageBox(nullptr, L"mysql_real_connect", L"提示", 0);
		return FALSE;
	}
	mysql_query(conn, "set names gbk");//utf-8和ansi(gb2312,gbk)
	//mysql_query(conn, "use worker");
	return TRUE;
}

CApp::CApp()
{
	// 支持重新启动管理器
	m_dwRestartManagerSupportFlags = AFX_RESTART_MANAGER_SUPPORT_RESTART;
}

CApp theApp;// CApp 初始化	唯一的 CApp 对象

BOOL CApp::InitInstance()	// 将所有重要的初始化放置在 InitInstance 中
{
	if (!ConnectDB())
		return FALSE;	
	CLoginDlg ldlg;
	if (ldlg.DoModal() == IDOK)
	{
		CMainDlg dlg;
		INT_PTR nResponse = dlg.DoModal();
	}
	return FALSE;
}

void CApp::DisplayError(CString sSQL)
{
	CString str;
	str.Format(_T("错误(%d):"), mysql_errno(&theApp.m_sql));//获取错误编号
	str = str + (LPCTSTR)_bstr_t(mysql_error(&theApp.m_sql)) + _T("\r\n") + sSQL; //罗列错误信息
	MessageBox(NULL, str, _T("提示"), MB_OK | MB_ICONERROR);
}

MainDlg.h

#pragma once
class CMainDlg : public CDialogEx		// CMainDlg 对话框
{
// 构造
	void DeleteInfo(CString str);
	void ModifyInfo(CString sNumb);
	void Refresh();
	CString GetLine(int nItem);
	void InitTitle();
	MYSQL& m_sql = theApp.m_sql;
	static void CorrentDate(CString& str)
	{
		str.Replace(_T('年'), _T('-'));
		str.Replace(_T('月'), _T('-'));
		str.Replace(_T('日'), _T('\0'));
	}
public:
	CMainDlg(CWnd* pParent = nullptr);	// 标准构造函数

#ifdef AFX_DESIGN_TIME
	enum { IDD = IDD_MAIN_DIG};		// 对话框数据
#endif

	protected:
	virtual void DoDataExchange(CDataExchange* pDX);	// DDX/DDV 支持

protected:		// 实现
	HICON m_hIcon;
	// 生成的消息映射函数
	virtual BOOL OnInitDialog();
	afx_msg void OnPaint();
	DECLARE_MESSAGE_MAP()
public:
	afx_msg void OnBnClickedDel();
	afx_msg void OnBnClickedAdd();
	afx_msg void OnBnClickedModeify();
	afx_msg void OnBnClickedSave();
	afx_msg void OnBnClickedCount();
};

MainDlg.cpp: 实现文件

#include "pch.h"
#include "framework.h"
#include "Employer_sql.h"
#include "MainDlg.h"
#include "CAdminDlg.h"
#include "CPassDlg.h"
#include "afxdialogex.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#endif
CMainDlg::CMainDlg(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_MAIN_DIG, pParent)
{
	m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

void CMainDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CMainDlg, CDialogEx)
	ON_WM_PAINT()
	ON_WM_QUERYDRAGICON()
	ON_BN_CLICKED(IDC_DEL, &CMainDlg::OnBnClickedDel)
	ON_BN_CLICKED(IDC_ADD, &CMainDlg::OnBnClickedAdd)
	ON_BN_CLICKED(IDC_MODEIFY, &CMainDlg::OnBnClickedModeify)
	ON_BN_CLICKED(IDC_SAVE, &CMainDlg::OnBnClickedSave)
 
	ON_BN_CLICKED(IDC_COUNT, &CMainDlg::OnBnClickedCount)
END_MESSAGE_MAP()
BOOL CMainDlg::OnInitDialog()
{
	CDialogEx::OnInitDialog();

	// 设置此对话框的图标。  当应用程序主窗口不是对话框时,框架将自动
	SetIcon(m_hIcon, TRUE);			// 设置大图标
	SetIcon(m_hIcon, FALSE);		// 设置小图标

	CDialogEx::OnInitDialog();
	InitTitle();
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	pList->InsertColumn(0, L"工号", LVCFMT_LEFT, 120);
	pList->InsertColumn(1, L"姓名", LVCFMT_LEFT, 130);
	pList->InsertColumn(2, L"工资", LVCFMT_LEFT, 130);
	pList->InsertColumn(3, L"入职日期", LVCFMT_LEFT, 180);
	pList->SetExtendedStyle(LVS_EX_GRIDLINES | LVS_EX_FULLROWSELECT);
	Refresh();

	return TRUE;  // 除非将焦点设置到控件,否则返回 TRUE
}

void CMainDlg::OnPaint()
{
		CPaintDC dc(this); // 用于绘制的设备上下文
}

CString CMainDlg::GetLine(int nItem)
{
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	CString str;
	int i = -1;
	while (++i<4)
	{
		if (i > 0)
			str += _T(",");
		str += pList->GetItemText(nItem, i);
	}
	return str;
}

void CMainDlg::InitTitle()
{
	CString str;
	GetWindowText(str);
	str += _T("  当前账号:") + theApp.m_sName + _T("【") +
		(theApp.m_nPrior ? _T("普通") : _T("高级")) + _T("】");
	SetWindowText(str);
	if (theApp.m_nPrior)
		SetDlgItemText(IDC_COUNT,_T("修改密码"));
}

void CMainDlg::Refresh()
{
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	pList->DeleteAllItems();
	int n = mysql_query(&m_sql, "SELECT * FROM t_worker");
	if (n)
	{
		MessageBox(L"mysql_query");
		return;
	}
	auto res = mysql_store_result(&m_sql);
	if (!res)
	{
		MessageBox(L"mysql_store_result");
		return;
	}
	MYSQL_ROW row;
	int i = 0;
	while (row = mysql_fetch_row(res))//_bstr_t既可以从宽版转向窄版 双向通道
	{
		_bstr_t str(*row++);
		pList->InsertItem(i, str);
		str = *row++;
		pList->SetItemText(i, 1, str);
		str = *row++;
		pList->SetItemText(i, 2, str);
		str = *row++;
		pList->SetItemText(i, 3, str);
		++i;
	}

}

void CMainDlg::DeleteInfo(CString str)
{
	char sSQL[256];
	sprintf_s(sSQL,_countof(sSQL),"DELETE FROM t_worker WHERE f_numb ='%s'", (LPCSTR)_bstr_t(str));
	int n = mysql_query(&m_sql, sSQL);
	if (n)
	{
		MessageBox(_T("ModifyInfo"),_T("删除失败"),0);
		return;
	}
}

void CMainDlg::OnBnClickedDel()
{
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	POSITION pos = pList->GetFirstSelectedItemPosition(); 
	if (!pos)
	{
		MessageBox(_T("请选中一行再进行删除"), _T("提示"));
		return;
	}
	while (pos)	//不断地向下循环
	{
		int i = pList->GetNextSelectedItem(pos);
		CString str = GetLine(i);
		if (MessageBox(str + _T("\r\n你确定要删除这一行吗?"),_T("提示"),MB_YESNO)==IDYES)
		{
			DeleteInfo(pList->GetItemText(i, 0));
		}
	}
	Refresh();
}

void CMainDlg::OnBnClickedAdd()
{
	

}

void CMainDlg::ModifyInfo(CString sNumb)
{
	CString str, sSQL;
	GetDlgItemText(IDC_NAME, str);
	sSQL = _T("UPDATE t_worker SET f_name = '") + str;
	GetDlgItemText(IDC_SALARY, str);
	sSQL += _T("',f_sala ='")+str;
	GetDlgItemText(IDC_DATETIME	, str);
	CorrentDate(str);
	sSQL += _T("',f_date='") + str;
	sSQL += _T("' WHERE f_numb='") + sNumb;
	sSQL += _T("'"); //sSQL += _T("'\'");
	int n = mysql_query(&m_sql, _bstr_t(sSQL)); //CString 到const char* 的转换
	if (n)
	{
		MessageBox(_T("ModifyInfo"), _T("修改失败"), 0);
		return;
	}
}
void CMainDlg::OnBnClickedModeify()
{
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	POSITION pos = pList->GetFirstSelectedItemPosition();
	if (!pos)
	{
		MessageBox(_T("请选中一行再进行修改"), _T("提示"));
		return;
	}
	int i = pList->GetNextSelectedItem(pos);
	CString str = GetLine(i);
	if (MessageBox(str + _T("\r\n你确定要修改这一行吗?"), _T("提示"), MB_YESNO) == IDYES)
	{
		ModifyInfo(pList->GetItemText(i,0));
		Refresh();
	}
}

void CMainDlg::OnBnClickedSave()
{

}

void CMainDlg::OnBnClickedCount()
{
	if (theApp.m_nPrior)
	{
		CPassDlg dlg;
		dlg.DoModal();
	}
	else
	{
		CAdminDlg dlg;
		dlg.DoModal();
	}
}

CLoginDlg.h

#pragma once
#include <afxdialogex.h>
class CLoginDlg :public CDialogEx
{
	DECLARE_DYNAMIC(CLoginDlg)
public:
	CLoginDlg(CWnd* pParent = nullptr);   // 标准构造函数
	virtual ~CLoginDlg();

#ifdef AFX_DESIGN_TIME
	enum { IDD = IDD_LOGIN_DLG };	// 对话框数据
#endif
protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持

	DECLARE_MESSAGE_MAP()
public:
	virtual BOOL OnInitDialog();
	afx_msg void OnBnClickedOk();
};

CLoginDlg.cpp: 实现文件

#include "pch.h"
#include "afxdialogex.h"
#include "CLoginDlg.h"
#include "Employer_sql.h"

IMPLEMENT_DYNAMIC(CLoginDlg, CDialogEx)
CLoginDlg::CLoginDlg(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_LOGIN_DLG, pParent)		// CLoginDlg 对话框
{

}

CLoginDlg::~CLoginDlg()
{
}

void CLoginDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CLoginDlg, CDialogEx)
	ON_BN_CLICKED(IDOK, &CLoginDlg::OnBnClickedOk)
END_MESSAGE_MAP()

BOOL CLoginDlg::OnInitDialog()
{
	CDialogEx::OnInitDialog();
	HICON hIcon = theApp.LoadIcon(IDR_MAINFRAME);
	this->SetIcon(hIcon, FALSE);
	CEdit* pEdit = (CEdit*)GetDlgItem(IDC_USERNAME);
	pEdit->LimitText(10); 
	pEdit = (CEdit*)GetDlgItem(IDC_PASS);
	pEdit->LimitText(20);
	return TRUE;  // return TRUE unless you set the focus to a control
	// 异常: OCX 属性页应返回 FALSE
}
/*	float f = 988;
	int n = int(f);//构造C语言不支持
	int n = (int)f;//强转 C语言支持*/
void CLoginDlg::OnBnClickedOk()
{
	CString sName, sPass;
	GetDlgItemText(IDC_USERNAME, sName);
	GetDlgItemText(IDC_PASS, sPass);
	CString sSQL;
	//BINARY  的SQL语句代表区分大小写,默认是不区分
	sSQL.Format(_T("SELECT * FROM t_admin WHERE f_name='%s' AND BINARY f_pass='%s'"),
		(LPCTSTR)sName, (LPCTSTR)sPass);

	if (mysql_query(&theApp.m_sql, (LPCSTR)_bstr_t(sSQL))) //什么也不写代表!0 加!就是等于0
	{
		CApp::DisplayError(sSQL);
		return;
	}

	auto res = mysql_store_result(&theApp.m_sql);
	if (!res)
	{
		CApp::DisplayError(_T("获取结果集失败!"));
		return;
	}
	if (mysql_num_rows(res) > 0)
	{
		auto row = mysql_fetch_row(res);
		theApp.m_sName = *row++;
		theApp.m_sPass = *row++;
		theApp.m_nPrior = atoi(*row);
		EndDialog(IDOK);
	}
	else
	{
		MessageBox(_T("账号或密码错误,请重新输入!"), _T("提示"), MB_OK | MB_ICONERROR);
		SetDlgItemText(IDC_USERNAME, _T(""));
		SetDlgItemText(IDC_PASS, _T(""));
		this->SetFocus();
	}
}

CAdminDlg.h: 实现文件

#pragma once
#include "afxdialogex.h"
class CAdminDlg : public CDialogEx
{
	DECLARE_DYNAMIC(CAdminDlg)
	void Refresh();
	bool CheckName(CString sName);
public:
	CAdminDlg(CWnd* pParent = nullptr);   // 标准构造函数
	virtual ~CAdminDlg();

#ifdef AFX_DESIGN_TIME
	enum { IDD = IDD_COUNT };// 对话框数据
#endif
protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持
	DECLARE_MESSAGE_MAP()
public:
	virtual BOOL OnInitDialog();
	afx_msg void OnBnClickedAdd();
	afx_msg void OnBnClickedDel();
	afx_msg void OnBnClickedUpdate();
};

CAdminDlg.cpp: 实现文件

#include "pch.h"
#include "Employer_sql.h"
#include "afxdialogex.h"
#include "CAdminDlg.h"
IMPLEMENT_DYNAMIC(CAdminDlg, CDialogEx)

CAdminDlg::CAdminDlg(CWnd* pParent /*=nullptr*/)// CAdminDlg 对话框
	: CDialogEx(IDD_COUNT, pParent)
{

}
CAdminDlg::~CAdminDlg()
{
}

void CAdminDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CAdminDlg, CDialogEx)
	ON_BN_CLICKED(IDC_ADD, &CAdminDlg::OnBnClickedAdd)
	ON_BN_CLICKED(IDC_DEL, &CAdminDlg::OnBnClickedDel)
	ON_BN_CLICKED(IDC_UPDATE, &CAdminDlg::OnBnClickedUpdate)
END_MESSAGE_MAP()

void CAdminDlg::Refresh()
{
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	pList->DeleteAllItems();
	int n = mysql_query(&theApp.m_sql, "SELECT * FROM t_admin");
	if (n)
	{
		MessageBox(L"mysql_query");
		return;
	}
	auto res = mysql_store_result(& theApp.m_sql);
	if (!res)
	{
		MessageBox(L"mysql_store_result");
		return;
	}
	MYSQL_ROW row;
	int i = 0;
	while (row = mysql_fetch_row(res)) 
	{
		_bstr_t str(*row++);
		pList->InsertItem(i, str);
		str = *row++; 
		pList->SetItemText(i, 1, str);
	//	pList->SetItemText(i, 2, ('1'== **row)?_T("普通"):_T("高级"));
		pList->SetItemText(i, 2, atoi(*row) ? _T("普通") : _T("高级")); //指针数组和二级指针
		++i;
	}
	mysql_free_result(res);
}

BOOL CAdminDlg::OnInitDialog()	
{
	CDialogEx::OnInitDialog();

	CComboBox* pCombox = (CComboBox*)GetDlgItem(IDC_PRIOR);
	pCombox->AddString(_T("普通")); //向尾部插入 关闭掉控件的排序属性,才会按照插入的顺序显示,否则会帮你对文字进行排序
	pCombox->AddString(_T("高级"));
	pCombox->SetCurSel(0);

	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	pList->InsertColumn(0, L"账号", LVCFMT_LEFT, 150);
	pList->InsertColumn(1, L"密码", LVCFMT_LEFT, 160);
	pList->InsertColumn(2, L"权限", LVCFMT_LEFT, 160);
	pList->SetExtendedStyle(LVS_EX_GRIDLINES | LVS_EX_FULLROWSELECT);
	Refresh();
	return TRUE;  // return TRUE unless you set the focus to a control
	// 异常: OCX 属性页应返回 FALSE
}

bool CAdminDlg::CheckName(CString sName)
{
	auto pList = (CListCtrl*)GetDlgItem(IDC_LIST);
	pList->DeleteAllItems();
	CString sSQL= _T("SELECT * FROM t_admin WHERE f_name='")+sName+_T("'");
	int n = mysql_query(&theApp.m_sql, (_bstr_t)sSQL);
	if (n)
	{
		CApp::DisplayError(sSQL);
		return false;
	}
	auto res = mysql_store_result(&theApp.m_sql);
	if (!res)
	{
		CApp::DisplayError(_T("mysql_store_result"));
		return false;
	}
	bool b = mysql_num_rows(res) > 0;
	mysql_free_result(res);
	return b;
}

void CAdminDlg::OnBnClickedAdd()
{
	CString sName, sPass, sPrior;
	GetDlgItemText(IDC_NAME, sName);
	if (CheckName(sName))
	{
		MessageBox(_T("你输入的账号已存在,请重新输入"), _T("提示"), MB_ICONERROR);
		return;
	}
	GetDlgItemText(IDC_PASS, sPass);
	GetDlgItemText(IDC_PRIOR, sPrior);
	int nPrior = sPrior == _T("普通");
	CString sSQL;
	sSQL.Format(_T("INSERT INTO t_admin VALUES('%s','%s','%d')"), sName, sPass, nPrior);
	int n = mysql_query(&theApp.m_sql, (_bstr_t)sSQL);
	if (n)
		CApp::DisplayError(sSQL);
	else
		Refresh();

}

void CAdminDlg::OnBnClickedDel()
{
	 
}

void CAdminDlg::OnBnClickedUpdate()
{
	 
}

CPassDlg.h

#pragma once
#include "afxdialogex.h"
class CPassDlg : public CDialogEx
{
	DECLARE_DYNAMIC(CPassDlg)
	bool ChangePass(CString sPass);
public:
	CPassDlg(CWnd* pParent = nullptr);   // 标准构造函数
	virtual ~CPassDlg();

#ifdef AFX_DESIGN_TIME
	enum { IDD = IDD_PASS_DLG };
#endif
protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持
	DECLARE_MESSAGE_MAP()
public:
	afx_msg void OnBnClickedOk();
};

CPassDlg.cpp: 实现文件

#include "pch.h"
#include "Employer_sql.h"
#include "afxdialogex.h"
#include "CPassDlg.h"
IMPLEMENT_DYNAMIC(CPassDlg, CDialogEx)

CPassDlg::CPassDlg(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_PASS_DLG, pParent)
{

}
CPassDlg::~CPassDlg()
{
}
void CPassDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CPassDlg, CDialogEx)
	ON_BN_CLICKED(IDOK, &CPassDlg::OnBnClickedOk)
END_MESSAGE_MAP()

bool CPassDlg::ChangePass(CString sPass)
{
	CString sSQL;
	sSQL.Format(_T("UPDATE t_admin SET f_pass ='%s' WHERE f_name ='%s'"), (LPCTSTR)sPass,(LPCTSTR)theApp.m_sName);
	int n = mysql_query(&theApp.m_sql, (_bstr_t)sSQL);
	if (!n)
	{
		theApp.m_sPass = sPass;
		return true;
	}
	CApp::DisplayError(sSQL);
	return false;
}

void CPassDlg::OnBnClickedOk()
{
	CString sOld, sNew, sConf;
	GetDlgItemText(IDC_OLDPASS, sOld);
	if (sOld.IsEmpty())
	{
		MessageBox(_T("旧密码不能为空"), _T("提示"), MB_ICONERROR);
		SetFocus();
		return;
	}
	if (sOld!=theApp.m_sPass)
	{
		MessageBox(_T("旧密码错误"), _T("提示"), MB_ICONERROR);
		SetFocus();
		return;
	}
	GetDlgItemText(IDC_NEWPASS, sNew);
	if (sNew.IsEmpty())
	{
		MessageBox(_T("新密码不能为空"), _T("提示"), MB_ICONERROR);
		SetFocus();
		return;
	}
	GetDlgItemText(IDC_CONFPASS, sConf);
	if (sConf.IsEmpty())
	{
		MessageBox(_T("确认密码不能为空"), _T("提示"), MB_ICONERROR);
		SetFocus();
		return;
	}
	if (sConf!=sNew)
	{
		MessageBox(_T("两次密码输入的不一致,请重新输入"), _T("提示"), MB_ICONERROR);
		SetFocus();
		return;
	}
	if (ChangePass(sNew))
	{
		EndDialog(IDOK);
		MessageBox(_T("密码修改成功"), _T("提示"), MB_ICONINFORMATION);
	}
	else
	{
		MessageBox(_T("密码修改失败"), _T("提示"), MB_ICONINFORMATION);
	}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/679253.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

入坑 TS(一)

1、TS 采用类型后置的语法 const str: string "我是字符串"; const num: number "我是数值"; const bool: boolean false;函数怎么写&#xff1f; // 有返回值 function sayHello(str: string): string {return str; } // 无返回值 function sayHello…

Java throws关键字

Java的throws关键字用于声明异常。它向程序员提供了可能发生异常的信息。 因此&#xff0c;最好为程序员提供异常处理代码&#xff0c;以便保持程序的正常流程。 异常处理主要用于处理已检查异常。如果出现任何未检查的异常&#xff0c;例如NullPointerException&#xff0c;则…

jjy-shareV2.0一键分享到微博,QQ空间,QQ好友,微信

介绍 jjy-shareV2.0一键分享到微博&#xff0c;QQ空间&#xff0c;QQ好友&#xff0c;微信 作者&#xff1a;极纪元-橙 作者博客&#xff1a;https://cplvfx.blog.csdn.net/ 码云Gitee&#xff1a;橙cplvfx极纪元 (cplvfx) - Gitee.com 项目地址&#xff1a;jjy-shareV2.…

登录认证(全集)--jwt,Filter,Interceptor详细说明

一、登录校验 问题&#xff1a;在未登录情况下&#xff0c;我们也可以直接访问部门管理、员工管理等功能。由于浏览器与web服务器中的数据交互是通过HTTP协议的&#xff0c;而HTTP协议是无状态的–即每个页面中的请求和响应都是独立的&#xff0c;没有状态存在。所以我们需要进…

WordPress网站的robots文件代码怎样写比较好

本文记载和介绍的是wordpress的robots.txt的在哪儿&#xff1f;以及如何修改robots文件来禁止搜索引擎爬取/ajax目录下的文章。以及如何优化WordPress网站的robots文件 wordpress设置robots文件的目录&#xff1a;/wp-includes/functions.php&#xff0c;然后搜索do_robotstxt…

【雕爷学编程】Arduino动手做(123)---Multi-function扩展板

37款传感器与执行器的提法&#xff0c;在网络上广泛流传&#xff0c;其实Arduino能够兼容的传感器模块肯定是不止这37种的。鉴于本人手头积累了一些传感器和执行器模块&#xff0c;依照实践出真知&#xff08;一定要动手做&#xff09;的理念&#xff0c;以学习和交流为目的&am…

随机数检测(一)

随机数检测&#xff08;一&#xff09;- 随机数自测试概述 1 概述2 产品形态划分和检测项目3 测试方式3.1 概述3.2 单比特频数检测方法3.3块内频数检测方法 1 概述 随机数发生器设计完成后&#xff0c;使用随机数发生器的产品需对其执行测试&#xff0c;防止应用过程中产生不合…

Redis的数据类型及对应的数据结构(二)

接上篇&#xff1a;Redis的数据类型及对应的数据结构&#xff08;一&#xff09;_鱼跃鹰飞的博客-CSDN博客 本篇主要讨论剩下的几种数据结构的应用场景 应用场景 集合的主要几个特性&#xff0c;无序、不可重复、支持并交差等操作。 因此 Set 类型比较适合用来数据去重和保…

卧剿,6万字!30个方向130篇!CVPR 2023 最全 AIGC 论文!一口气读完。

一杯奶茶&#xff0c;成为 AIGCCV 视觉前沿弄潮儿&#xff01; 25个方向&#xff01;CVPR 2022 GAN论文汇总 35个方向&#xff01;ICCV 2021 最全GAN论文汇总 超110篇&#xff01;CVPR 2021 最全GAN论文梳理 超100篇&#xff01;CVPR 2020 最全GAN论文梳理 在最新的视觉顶会 C…

Java多重捕获块

try块后面可以跟随一个或多个catch块。每个catch块必须包含一个不同的异常处理程序。因此&#xff0c;如果您在不同的异常发生时需要执行不同的任务&#xff0c;请使用Java多重捕获块。 需要记住的要点 一次只会发生一个异常&#xff0c;同时只有一个catch块被执行。 所有的ca…

实训五:数据库安全控制 - MySQL数据库 - 授权与撤销授权

MySQL数据库 - 授权与撤销授权 第1关&#xff1a;数据库授权任务描述相关知识用户管理授权方式 编程要求测试说明参考代码 第2关&#xff1a;数据库撤销权限任务描述相关知识撤销权限 编程要求测试说明参考代码 第1关&#xff1a;数据库授权 任务描述 本关任务&#xff1a;新…

Ubuntu安装Anaconda详细步骤(Ubuntu22.04.1,Anaconda3-2023.03)

本文主要讲述了在Ubuntu中安装anaconda的具体步骤 准备环境&#xff1a;Ubuntu22.04.1&#xff0c;Anaconda3 1.下载Anaconda3 在清华镜像下载Linux版本的anaconda 清华镜像官网Anaconda下载 我选择的是Anaconda3-2023.03-Linux-x86_64.sh 下载好的Anaconda3-2023.03-Linux-…

拦截器Interceptor及与过滤器Filter的区别

统一拦截–拦截器Interceptor 1.概述 概念:是一种动态拦截方法调用的机制&#xff0c;类似于过滤器。Spring框架中提供的&#xff0c;用来动态拦截控制器方法的执行。作用:拦截请求&#xff0c;在指定的方法调用前后&#xff0c;根据业务需要执行预先设定的代码。与过滤器Fil…

【Java|多线程与高并发】设计模式-单例模式(饿汉式,懒汉式和静态内部类)

文章目录 1. 前言2. 单例模式3. 如何保证一个类只有一个实例4. 饿汉式单例模式5. 懒汉式单例模式6. 实现线程安全的懒汉式单例7. 静态内部类实现单例模式8. 总结 1. 前言 设计模式是一种在软件开发中常用的解决复杂问题的方法论。它提供了一套经过验证的解决方案&#xff0c;用…

通信原理概述

通信是指人们通过某种媒介进行信息传递。通过某种介质或通道&#xff0c;将信息从一个地点传递到另一个地点的过程。通信可以是人与人之间的交流&#xff0c;也可以是设备、系统或网络之间的数据传输。 通信信号的分类方法&#xff1a; 1&#xff09;模拟信号和数字信号(从信号…

数字游戏:如何统计能整除数字的位数?

本篇博客会讲解力扣“2520. 统计能整除数字的位数”的解题思路&#xff0c;这是题目链接。 本题的思路是&#xff1a;取出每一位&#xff0c;判断是否能整除。 如何取出每一位呢&#xff1f;可以采用“mod10除10”的策略。即&#xff1a;每次mod10取出最后一位数&#xff0c;再…

2022年软件测试面试题大全【含答案】

一、面试基础题 简述测试流程: 1、阅读相关技术文档&#xff08;如产品PRD、UI设计、产品流程图等&#xff09;。 2、参加需求评审会议。 3、根据最终确定的需求文档编写测试计划。 4、编写测试用例&#xff08;等价类划分法、边界值分析法等&#xff09;。 5、用例评审(…

C++面向对象 this指针 构造函数 析构函数 拷贝构造 友元

C面向对象 面向对象概念类与对象的区别 C中类的设计设计实例实例解释共有和私有类的认识 函数定义函数在类里定义和类外定义区别函数定义实例 C对象模型方案一:各对象完全独立地安排内存的方案方案二:各对象的代码区共用的方案: this指针this指针特点程序编译面向对象程序的过程…

【力扣刷题 | 第十四天】

目录 前言&#xff1a; 7. 整数反转 - 力扣&#xff08;LeetCode&#xff09; 面试题 16.05. 阶乘尾数 - 力扣&#xff08;LeetCode&#xff09; 总结; 前言&#xff1a; 今天仍然是无固定类型刷题&#xff0c; 7. 整数反转 - 力扣&#xff08;LeetCode&#xff09; 给你…

傅氏变换算法

半局积分算法的局限性是要求采样的波形为正弦波。当被采样的模拟量不是正弦波而是一个周期性时间函数时&#xff0c;可采用傅氏变换算法。傅氏变换算法来自于傅里叶级数&#xff0c;即一个周期性函数I&#xff08;t&#xff09;可用傅里叶级数展开为各次谐波的正弦项和余弦项之…