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

📄 pp.cpp

📁 九宫图游戏
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// pp.cpp : Defines the entry point for the application.
//

#include "stdafx.h"
#include "resource.h"
#include "stdio.h"
#include <time.h>
#include <fstream.h>

#define MAX_LOADSTRING 100
#define LEFT 150
#define TOP 20
#define RIGHT 450
#define BOTTOM 320
#define SIZE 100
#define	MOVE_UP 38
#define MOVE_DOWN 40
#define MOVE_LEFT 37
#define MOVE_RIGHT 39
#define STOP 0
#define USER 1
#define AUTO 2
#define DISPLAY 3
#define LEN 10
#define FAIL -1

// Global Variables:
HINSTANCE hInst;								// current instance
TCHAR szTitle[MAX_LOADSTRING];								// The title bar text
TCHAR szWindowClass[MAX_LOADSTRING];								// The title bar text
int map[10]={0};//存储九宫图数据
int *stack,*stack_top;//自定义堆栈
int *knowledge=NULL,*knowledge_top=NULL;//存储知识,即已存储的状态即走法
int knowledge_len=0;//存储已存记录的长度(个数)
int sign;//标志当前游戏状态(停止、玩家、自动、演示)
long len;//堆栈长度
long max_len;//堆栈最大长度
BOOL searching;//正在用Search进行搜索的标志
HWND hwnd;//
BOOL study;//
FILE *fp;//外部文件
int playspeed=400;//演示速度
long step;//演示步数


// Foward declarations of functions included in this code module:
ATOM				MyRegisterClass(HINSTANCE hInstance);
BOOL				InitInstance(HINSTANCE, int);
LRESULT CALLBACK	WndProc(HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK	About(HWND, UINT, WPARAM, LPARAM);
void ReDraw();//重画九宫图
void NewGame();//开始新游戏
void Auto();//开启自动搜索
BOOL MoveUp();//向上移动
BOOL MoveLeft();//左
BOOL MoveRight();//右
BOOL MoveBottom();//下
int GetReverse();//获取当前状态的逆序数
BOOL Success();//判断是否成功
BOOL Search(int direct);//自动搜索的递归算法
BOOL Push();//将当前状态压入自定义的堆栈
void Pop();//出栈,放入当前状态
void ShowWaiting();//显示“Please Waiting”
void AutoSearch();//自动搜索的函数,被Auto调用,调用Search
void OpenStudy();//开启学习状态
void CloseStudy();//关闭学习状态
void ReadKnowledge();//读取已存状态
void SaveKnowledge();//保存状态
int SearchKnowledge();//在状态中搜索当前状态,如有,返回应走方向,否则返回0
void Study(int direct);//学习,保存当前状态及走法
int Judge();//在未搜索到的情况下判断走法
void GetDistance(int pos1,int pos2,BOOL& narrow,int& direct);//获得两点位置关系



int APIENTRY WinMain(HINSTANCE hInstance,
                     HINSTANCE hPrevInstance,
                     LPSTR     lpCmdLine,
                     int       nCmdShow)
{
 	// TODO: Place code here.
	MSG msg;
	HACCEL hAccelTable;

	// Initialize global strings
	LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
	LoadString(hInstance, IDC_PP, szWindowClass, MAX_LOADSTRING);
	MyRegisterClass(hInstance);

	// Perform application initialization:
	if (!InitInstance (hInstance, nCmdShow)) 
	{
		return FALSE;
	}

	hAccelTable = LoadAccelerators(hInstance, (LPCTSTR)IDC_PP);

	// Main message loop:
	while (GetMessage(&msg, NULL, 0, 0)) 
	{
		if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg)) 
		{
			TranslateMessage(&msg);
			DispatchMessage(&msg);
		}
	}

	return msg.wParam;
}



//
//  FUNCTION: MyRegisterClass()
//
//  PURPOSE: Registers the window class.
//
//  COMMENTS:
//
//    This function and its usage is only necessary if you want this code
//    to be compatible with Win32 systems prior to the 'RegisterClassEx'
//    function that was added to Windows 95. It is important to call this function
//    so that the application will get 'well formed' small icons associated
//    with it.
//
ATOM MyRegisterClass(HINSTANCE hInstance)
{
	WNDCLASSEX wcex;

	wcex.cbSize = sizeof(WNDCLASSEX); 

	wcex.style			= CS_HREDRAW | CS_VREDRAW;
	wcex.lpfnWndProc	= (WNDPROC)WndProc;
	wcex.cbClsExtra		= 0;
	wcex.cbWndExtra		= 0;
	wcex.hInstance		= hInstance;
	wcex.hIcon			= LoadIcon(hInstance, (LPCTSTR)IDI_PP);
	wcex.hCursor		= LoadCursor(NULL, IDC_ARROW);
	wcex.hbrBackground	= (HBRUSH)(COLOR_WINDOW+1);
	wcex.lpszMenuName	= (LPCSTR)IDC_PP;
	wcex.lpszClassName	= szWindowClass;
	wcex.hIconSm		= LoadIcon(wcex.hInstance, (LPCTSTR)IDI_SMALL);

	return RegisterClassEx(&wcex);
}

//
//   FUNCTION: InitInstance(HANDLE, int)
//
//   PURPOSE: Saves instance handle and creates main window
//
//   COMMENTS:
//
//        In this function, we save the instance handle in a global variable and
//        create and display the main program window.
//
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
   HWND hWnd;

   hInst = hInstance; // Store instance handle in our global variable

   hWnd = CreateWindow(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,
      CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInstance, NULL);

   if (!hWnd)
   {
      return FALSE;
   }
	hwnd=hWnd;
   ShowWindow(hWnd, nCmdShow);
   UpdateWindow(hWnd);

   return TRUE;
}

//
//  FUNCTION: WndProc(HWND, unsigned, WORD, LONG)
//
//  PURPOSE:  Processes messages for the main window.
//
//  WM_COMMAND	- process the application menu
//  WM_PAINT	- Paint the main window
//  WM_DESTROY	- post a quit message and return
//
//
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
	int wmId, wmEvent;
	PAINTSTRUCT ps;
	HDC hdc;
	TCHAR szHello[MAX_LOADSTRING];
	int the_Direct;
//	HMENU hmenu;
	LoadString(hInst, IDS_HELLO, szHello, MAX_LOADSTRING);

	switch (message) 
	{
		case WM_CREATE:
			sign=STOP;
			stack=(int*)malloc(sizeof(int)*100000*LEN);
			stack_top=stack;
			len=0;
			max_len=100000;//初始化堆栈
			study=false;
			ReadKnowledge();//读取已存知识
			break;
		case WM_COMMAND:
			wmId    = LOWORD(wParam); 
			wmEvent = HIWORD(wParam); 
			// Parse the menu selections:
			switch (wmId)
			{
				case IDM_NEW:
					NewGame();//开始新游戏
					break;
				case IDM_AUTO:
					Auto();//开启自动搜索
					break;
				case IDM_STUDY:
					//hmenu=GetMenu(hWnd);
					if(study==false)
					{
					//	CheckMenuItem(hmenu,IDM_STUDY,MF_CHECKED);
						OpenStudy();
					//	study=true;
					}
					else
					{						
					//	CheckMenuItem(hmenu,IDM_STUDY,MF_UNCHECKED);
						CloseStudy();//打开、关闭学习开关
					//	study=false;
					}
					break;
				case IDM_LOWSPEED:
					playspeed=800;
					break;
				case IDM_MIDDLESPEED:
					playspeed=400;
					break;
				case IDM_HIGHSPEED:
					playspeed=100;
					break;
				case IDM_ABOUT:
				   DialogBox(hInst, (LPCTSTR)IDD_ABOUTBOX, hWnd, (DLGPROC)About);
				   break;
				case IDM_EXIT:
				   DestroyWindow(hWnd);
				   if(study==true)
					   CloseStudy();//存储已存状态
				   break;
				default:
				   return DefWindowProc(hWnd, message, wParam, lParam);
			}
			break;
		case WM_PAINT:
			hdc = BeginPaint(hWnd, &ps);
			 //TODO: Add any drawing code here...
			RECT rt;
			GetClientRect(hWnd, &rt);
			DrawText(hdc, szHello, strlen(szHello), &rt, DT_CENTER);
			EndPaint(hWnd, &ps);
			ReDraw();
			break;
		case WM_KEYDOWN:
			if(sign!=USER)
				return 0;
			the_Direct=int(wParam);
			switch(the_Direct)
			{
			case MOVE_UP:
				if(MoveUp()==false)
					MessageBeep(MB_OK);
				break;
			case MOVE_DOWN:
				if(MoveBottom()==false)
					MessageBeep(MB_OK);
				break;
			case MOVE_LEFT:
				if(MoveLeft()==false)
					MessageBeep(MB_OK);
				break;
			case MOVE_RIGHT:
				if(MoveRight()==false)//接收键盘输入
					MessageBeep(MB_OK);
				break;
			default:
				return 0;
			}
			ReDraw();
			if(Success()==true)
			{
				if(MessageBox(hWnd,"再来一局?","胜利!!!",MB_OKCANCEL)==IDOK)
					NewGame();
				else
					sign=STOP;
			}
			break;
		case WM_DESTROY:
			PostQuitMessage(0);
			free(stack);
			SaveKnowledge();
			break;
		default:
			return DefWindowProc(hWnd, message, wParam, lParam);
   }
   return 0;
}

// Mesage handler for about box.
LRESULT CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
	switch (message)
	{
		case WM_INITDIALOG:
				return TRUE;

		case WM_COMMAND:
			if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL) 
			{
				EndDialog(hDlg, LOWORD(wParam));
				return TRUE;
			}
			break;
	}
    return FALSE;
}

void ReDraw()
{
	HDC hdc;
	hdc=GetDC(hwnd);
	HBRUSH hBr1,hBr2;
	LPPOINT lppoint=NULL;

	hBr1=(HBRUSH)GetStockObject(DKGRAY_BRUSH);
	SelectObject(hdc,hBr1);
	Rectangle(hdc,LEFT,TOP,RIGHT,BOTTOM);
	if(map[0]!=0)
	{
		hBr2=(HBRUSH)GetStockObject(GRAY_BRUSH);
		SelectObject(hdc,hBr2);
		int x,y;
		switch(map[0])
		{
		case 1:
			x=1;y=1;break;
		case 2:
			x=2;y=1;break;
		case 3:
			x=3;y=1;break;
		case 4:
			x=1;y=2;break;
		case 5:
			x=2;y=2;break;
		case 6:
			x=3;y=2;break;
		case 7:
			x=1;y=3;break;
		case 8:
			x=2;y=3;break;
		case 9:
			x=3;y=3;break;
		}
		Rectangle(hdc,LEFT+(x-1)*100,TOP+(y-1)*100,LEFT+x*100,TOP+y*100);
		//Draw the text
		for(int j=1;j<=9;j++)
		{
			switch(j)
			{
			case 1:
				x=1;y=1;break;
			case 2:
				x=2;y=1;break;
			case 3:
				x=3;y=1;break;
			case 4:
				x=1;y=2;break;
			case 5:
				x=2;y=2;break;
			case 6:
				x=3;y=2;break;
			case 7:
				x=1;y=3;break;
			case 8:
				x=2;y=3;break;
			case 9:
				x=3;y=3;break;
			}
			if(j!=map[0])
			{
				char out_text[2];
				sprintf(out_text,"%d",map[j]);
				TextOut(hdc,LEFT+(x-1)*100+45,TOP+(y-1)*100+45,out_text,1);
			}
		}
		DeleteObject(hBr2);
	}
	MoveToEx(hdc,LEFT+100,TOP,lppoint);
	LineTo(hdc,LEFT+100,BOTTOM);
	MoveToEx(hdc,LEFT+200,TOP,lppoint);
	LineTo(hdc,LEFT+200,BOTTOM);
	MoveToEx(hdc,LEFT,TOP+100,lppoint);
	LineTo(hdc,RIGHT,TOP+100);
	MoveToEx(hdc,LEFT,TOP+200,lppoint);
	LineTo(hdc,RIGHT,TOP+200);
	DeleteObject(hBr1);
	if(sign==DISPLAY)
	{
		char dstep[20];
		sprintf(dstep,"(Steps:%5ld     /",step);
		TextOut(hdc,230,345,dstep,18);
	}
	ReleaseDC(hwnd,hdc);
}

void NewGame()
{
	int i,j,k,temp;
	if(sign==USER)//判断状态
	{
		if(MessageBox(hwnd,"放弃当前游戏?","提示",MB_OKCANCEL)==IDCANCEL)
		{
			return;
		}
		if(MessageBox(hwnd,"当前游戏是否无解?","提示",MB_OKCANCEL)==IDOK)
			Study(FAIL);//如果此状态无解,也存入状态表中
	}
	srand((unsigned)time(NULL));
	map[0]=9;
	for(i=1;i<9;i++)
		map[i]=i;
	map[9]=0;
	do{
		for(i=0;i<10;i++)
		{
			j=rand()%9+1;
			k=rand()%9+1;
			temp=map[j];
			map[j]=map[k];
			map[k]=temp;
			if(map[j]==0)
				map[0]=j;
			if(map[k]==0)
				map[0]=k;
		}
	}while(GetReverse()==0);//随机产生一个状态
	ReDraw();
	sign=USER;
	stack_top=stack;
	len=0;
}
void Auto()
{
	if(sign!=USER)
		return;
	sign=AUTO;
	DWORD ID1;
	DWORD ID2;
	searching=true;
	CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)ShowWaiting,NULL,0,&ID1);
	//开启搜索线程
	CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)AutoSearch,NULL,0,&ID2);
	//开启显示等待线程
	//主线程接受用户输入
}
BOOL MoveUp()
{
	if(map[0]==1||map[0]==2||map[0]==3)

⌨️ 快捷键说明

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