#平台
Ubuntu12
ncurse图像
#(一)ncurse的使用
由于我是刚刚开始的接触的一个小白,打算从事嵌入式软件方向的一名的准大三学生。在学校感觉无法系统学习嵌入式。所以在外面报了个培训班。现在刚刚开始第一个项目。
对于ncurse老师告诉我只是记住基本格式就行,其他可以上网找资料。
ncurse的初始化:
#define UP 1
#define DOWN -1
#define LEFT 2
#define RIGHT -2
void initNcurse()//ncurses的初始化
{
initscr();
keypad(stdscr,1);
noecho();//显示按键的值
}
#include "curses.h"
#include "stdio.h"
int main()
{
initscr();//ncures界面的初始化函数
printw("This is curses window.\n");//在ncurse模式下的printf
getch();//等待用户输入,如果没有这句话,程序就退出了,看不到运行>结果,也就是上面那句话。
endwin();//程序退出,调用改变函数来恢复shell终端的显示,没有这句>话,shell终端乱码,坏掉。
return 0;
}
以上是ncurse的基本格式,开发也是从这里开始。
(二)#地图的构建
我们要构造的地图是20*20的,行用“–”表示,列用“|”表示;
首先我们先打印第0行和第0列和第19列
int hang;
int lie;
for(hang=0;hang<20;hang++){
//==================================================================
if(hang==0){//打印第0行
for(lie=0;lie<20;lie++){ 打印第一行
printw("--");
}
printw("\n");
for(lie=0;lie<=20;lie++){打印边框
if(lie==0||lie==20){
printw("|");
}
else{
printw(" ");//注意这里是空两格(--,|的字节不同方便美观)
}
}
printw("\n");
}
在打印两边:
if(hang>0&&hang<19){//打印两边的界
for(lie=0;lie<=20;lie++){
if(lie==0||lie==20){
printw("|");
}
else{
printw(" ");
}
}
printw("\n");
}
最后封底:
if(hang==19){//打印最底下的一行
for(lie=0;lie<20;lie++){
printw("--");
}
printw("\n");
printw("by:hxx");
}
}
}
结果如图:
#(三)用链表构建一条蛇
struct Snake//构建蛇的结构体
{
int hang;
int lie;
struct Snake *next; //链表的节点
};
void initSnake()//添加有一条小蛇
{
struct Snake *p;
while(head!=NULL){
p=head;//临时保存被删结点的地址以备释放
head=head->next;//改变删除结点前驱结点的指针域
free(p);//释放
}
head=(struct Snake *)malloc(sizeof(struct Snake));
head->hang=2;//初始位置
head->lie=1;
head->next=NULL;
tail=head;
addNode();//添加结点
addNode();
addNode();
addNode();
}
int hasSnakeNode(int i,int j)//添加的位置和别添加的是否相同
{
struct Snake *p;
p=head;
while(p!=NULL){
if(p->hang==i&&p->lie==j){
return 1;
}
p=p->next;
}
return 0;
}
#构建食物
食物我们用“##”表示和构建蛇相似
void initFood()
{
int x=rand()%20;
int y=rand()%20;
food.hang=x;
food.lie=y;
}
int hasFood(int i,int j)
{
if(food.hang==i&&food.lie==j){
return 1;
}
return 0;
}```
##让蛇游走
让蛇移动就是在蛇链表上,删除头节点,在尾部加一个结点从而形成结点
```c
void addNode()//在蛇的尾部加新节点
{
new->next=NULL;
switch(dir)
{
case UP: new->hang=tail->hang-1;new->lie=tail->lie; break;
case DOWN: new->hang=tail->hang+1;new->lie=tail->lie; break;
case LEFT: new->hang=tail->hang;new->lie=tail->lie-1; break;
case RIGHT: new->hang=tail->hang;new->lie=tail->lie+1;break;
}
tail->next=new;//指向新节点的数据域
tail=new;//指向最后
}
void deleNode()
{
struct Snake *p;
p=head;//临时保存被删结点的地址以备释放
head=head->next;//改变删除结点前驱结点的指针域
free(p);//释放删除结点的空间
}
##如果当设碰见墙壁,和自己的身体,游戏重新开始
void moveSnake()//重新开始
{
struct Snake *p;
// struct Snake *new;
addNode();
if(hasFood(tail->hang,tail->lie)){//遇到吃的,就吃掉。
initFood();
}
else{
deleNode();
}
p=head;
if(ifSnakeDie()){
initSnake();
}
}
也要让界面刷新,不然就不还好看。。。。。。。
void* refreshJieMian()//刷新界面
{
while(1)
{
moveSnake();
gameMap();
refresh();//刷新界面
usleep(200000);
}
}
int ifSnakeDie()
{
struct Snake *p;
p=head;
if(tail->hang<0||tail->lie==0||tail->hang==20||tail->lie==20){
return 1;
}
while(p->next!=NULL)//判断是否和身体相撞
{
if(p->hang==tail->hang&&p->lie==tail->lie){
return 1;
}
p=p->next;
}
return 0;
}
#一下是对细节的优化
首先我的游戏有两个while循环,但是我们只能运行一个,所以我们这里就要,用到线程的知识。
#include <stdio.h>
#include <pthread.h>
#include <unistd.h>
struct Snake *head;
struct Snake *tail;
int key;
int dir;
struct Snake food;
void *fun(void *arg)
{
printf("I'm thread, Thread ID = %lu\n", pthread_self());
return NULL;
}
int main(int argc,char *argv[])
{
pthread_t tid;
int ret;
int arg=10;
int *thread_ret=NULL;
ret=pthread_create(&tid, NULL, fun, &arg);
if(ret!=0){
printf("Creat thread error!\n");
return -1;
}
printf("this is the main process.\n");
pthread_join(tid,(void**)&thread_ret);
sleep(1); // 在多线程环境中,父线程终止,全部子线程被迫终止
printf("thread_ret = %d\n", *thread_ret);
return 0;
}
是不是感觉有点难懂,但是我们用不了这么多,只要建立线程即可。
int main()
{
pthread_t t1;
pthread_t t2;
initNcurse();
initSnake();
gameMap();
pthread_create(&t1, NULL, refreshJieMian, NULL);
pthread_create(&t2, NULL, changDir, NULL);
while(1);
getch();
endwin();
return 0;
}
在main函数中建立依样画葫芦,即可。就可以实现同时进行。
同时我们也要确定方向
void turn(int direction)
{
if(abs(dir)!=abs(direction))
{
dir=direction;
}
}
void* changDir()
{
// int key;
while(1){
key=getch();
switch(key){
case KEY_DOWN:
turn(DOWN);
break;
case KEY_UP:
turn(UP);
break;
case KEY_LEFT:
turn(LEFT);
break;
case KEY_RIGHT:
turn(RIGHT);
break;
}
}
}
以上就是全部内容,这是本人的第一篇,技术文章,不足之处还望大佬批评。