⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 menu.cpp

📁 很好的学习C++源码,基于C++版学生管理系统
💻 CPP
字号:
#include "Menu.h"    //菜单类头文件


CMenu *CMenu::m_pNowMenu = NULL;  //静态成员类指针变量初始化为NULL
bool CMenu::bExitMarkDifferent = 0;

//函数功能:构造函数初始化菜单名、返回选项及该菜单下一些参数值
//输入参数:从形参获得字符串
//输出参数:无
//返回值: 无
//修改人:邹明上
//修改时间:2006.06.16
CMenu::CMenu(char* MenuName)
{
	m_pHead_Op  = &m_Back_Op;  //当有一菜单类对象产生时,就自动生成一个"0.退出管理系统"选项,且要做好后面菜单连接的初始化
	m_pTrail_Op = &m_Back_Op;
	m_pNow_Op   = &m_Back_Op;
	m_Back_Op.m_nOptionNumber = 0;
	m_Back_Op.m_pNextMenu  = NULL;
	m_Back_Op.m_NextOption = NULL;
	if(bExitMarkDifferent == 0)
	{
		strcpy(m_Back_Op.m_sOptionName,"退出管理系统");
		bExitMarkDifferent = 1;
	}
	else
	{
		strcpy(m_Back_Op.m_sOptionName,"返回");
	}
	m_nTotal_Op = 0;
	strcpy(m_sNowMenuName,MenuName);
}

//函数功能:构造函数什么也不做
//输入参数:无
//输出参数:无
//返回值: 无
//修改人:邹明上
//修改时间:2006.06.16
CMenu::CMenu()
{

}

//函数功能:析构函数实现释放链表曾用过的内存堆区空间
//输入参数:无
//输出参数:无
//返回值: 无
//修改人:邹明上
//修改时间:2006.06.16
CMenu::~CMenu()
{
	while(m_pHead_Op != &m_Back_Op)  //不能析构"0"返回选项的空间,因为他是栈区分配空间
	{
		m_pNow_Op = m_pHead_Op;
		m_pHead_Op = m_pHead_Op->m_NextOption;
		delete m_pNow_Op;
		//printf("\n每个菜下子菜单析构次数");
	}
	//printf("\n已成功完成一次菜单析构");
	//getch();
}

//函数功能:添加菜单选项菜单和该选项(子)菜单的下一级菜单地址
//输入参数:从形参获得选项菜单名和下一级菜单地址
//输出参数:无
//返回值: void空型
//修改人:邹明上
//修改时间:2006.06.16
void CMenu::Add(char* MenuName,CMenu* NextMenu)
{
	m_pNow_Op = new MenuOption;
	if(m_pHead_Op == &m_Back_Op)  //第一个选放置在"0.退出管理系统"选项的前面
	{
		m_pHead_Op  = m_pNow_Op;
		m_pTrail_Op = m_pNow_Op;
		m_pNow_Op->m_nOptionNumber = 1;
		m_pNow_Op->m_pNextMenu = NextMenu;
		strcpy(m_pNow_Op->m_sOptionName,MenuName);
		m_pNow_Op->m_NextOption = &m_Back_Op;
	}
	else   //当有第二个或是二个以上选项添加进来时,将其插入到尾指与"0.退出管理系统"之间
	{
		m_pNow_Op->m_nOptionNumber = m_pTrail_Op->m_nOptionNumber + 1;
		m_pNow_Op->m_pNextMenu = NextMenu;
		strcpy(m_pNow_Op->m_sOptionName,MenuName);
		m_pNow_Op->m_NextOption = &m_Back_Op;
		m_pTrail_Op->m_NextOption = m_pNow_Op;
		m_pTrail_Op = m_pNow_Op;
	}
	m_nTotal_Op ++;   //总共菜单选项总计数加1
}

//函数功能:设置当前菜单的前指针指向的上一级菜单地址
//输入参数:从型参获得上一级菜单首地址
//输出参数:无
//返回值: void空型
//修改人:邹明上
//修改时间:2006.06.16
void CMenu::SetFront(CMenu* FrontMenu)
{
	m_pFrontMenu = FrontMenu;  //设置当前菜单的上一级菜单地址,因为每一级菜单与菜单之间是两向链表
	if(m_pFrontMenu == NULL)
	{
		m_pNowMenu = this;
	}
}

//函数功能:显示菜单列表,若选择菜单中选项没有下一级菜单则返回该选项名称的首地址
//输入参数:键盘输入选项菜单值
//输出参数:显示菜单列表及输入参数
//返回值: 返回一个字符串首地址
//修改人:邹明上
//修改时间:2006.06.16
char* CMenu::ShowMenu(void)
{
	int  nInputVal = -1; //接收键盘输入的选项值
	bool bControlWhile = true; //控制while循环
	MenuOption* pMoveNow_Op = NULL; //指向预显示菜单节点首地址后,遍历显示该菜单列表选项
	/*---以下三个变量用于判断键盘输入---*/
	char cTemp = 'z';
	int nIfBack = 0;
	int nSure = 0;

	while(bControlWhile)
	{
		system("cls");
		pMoveNow_Op = m_pNowMenu->m_pHead_Op;
		cout << "\n\n\t\t\t\t" << m_pNowMenu->m_sNowMenuName << endl;
		cout <<  "\t\t\t\t   (PSMS欢迎您)" << endl;
		cout << "\n\t\t" <<"============================================="<<endl;
		while(pMoveNow_Op != NULL) //显示该菜单目录列表选项
		{
			cout << endl;
			cout << "\t\t\t     " << pMoveNow_Op->m_nOptionNumber << ". ";
			cout << pMoveNow_Op->m_sOptionName << endl;
			pMoveNow_Op = pMoveNow_Op->m_NextOption;
		}
		cout << endl;
		cout << "\t\t" <<"============================================="<<endl;
		printf("\t\t\t    请选择:");
		/*-------1.以下到2.位置是实现输入.显示只一位字符的程序代码-------*/
		if(nIfBack == 1)
		{
			printf(" ");
			nIfBack = 0;
		}
		else
		{
			printf("%c",cTemp);
		}
		nSure = 0;
		for(int nI = 0;nI < 1 && !nIfBack;nI ++)
		{
			fflush(stdin);
			cTemp = getch();

			switch(cTemp)
			{
				case 13:
					{
						nSure = 1;
						cTemp = 'z';
						break;
					}
				case 8:
					{
						nIfBack = 1;
						break;
					}
				case 27:
					{
						cTemp = '0';
					}
				default:
					{
						nInputVal = cTemp - 48;
						break;
					}
			}
		}
		/*------------------------2------------------------*/
		//下面有nInputVal 值的条件限制,主要是为了提高程序效率
		if(nSure == 1 && (nInputVal >= 0 && nInputVal <= m_pNowMenu->m_nTotal_Op))
		{
			pMoveNow_Op = m_pNowMenu->m_pHead_Op; //让指针重新回到链表头,做好重新遍历准备
			while(pMoveNow_Op != NULL) //查找输入选项数值,用来确定下一步做什么
			{
				if(nInputVal == 0)  //当输入的值是选项值"0"的情况,即"返回"
				{
					if(m_pNowMenu->m_pFrontMenu == NULL) //当前菜单的上一级没有时
					{
						bControlWhile = false;
						return "End";   //当前菜单是第一级菜单时,按下0键后,返回"End"结束字符串
					}
					else                //当前菜单有上级菜单的情况
					{
						g_nAddTime = 0; //当退出一次增加学生信息菜单后,让记录添加学生个数的计数器归零
						m_pNowMenu = m_pNowMenu->m_pFrontMenu; //当前菜单的上级菜单地址赋给要显示的当前指针,做好显示菜单的准备
					}
					break;
				}
				else if(nInputVal == pMoveNow_Op->m_nOptionNumber) //当输入的值与菜单选项值相等的情况
				{
					if(pMoveNow_Op->m_pNextMenu == NULL) //当前选项菜单有下一级子菜单
					{
						bControlWhile = false;
						return pMoveNow_Op->m_sOptionName;  //返回第几个菜单选项对应的字符串,如"按不同方式查寻学生信息"
					}
					else                               //当前选项菜单没有下一级子菜单
					{
						m_pNowMenu = pMoveNow_Op->m_pNextMenu; //当前指针等于下一级菜单地址,做好显示菜单准备
					}
					break;
				}
				pMoveNow_Op = pMoveNow_Op->m_NextOption;
			}
			nInputVal = -1;
			cTemp = 'z';
			nIfBack = 0;
			nSure = 0;  //重新初始化以上四个参数值
		}
	}
	return "0";
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -