精华内容
下载资源
问答
  • C语言个贪吃蛇游戏

    万次阅读 多人点赞 2020-02-19 08:24:09
    贪吃蛇是个非常经典的游戏,用C语言来实现也是个好玩的事情。这个游戏完后放在知乎,竟然点赞的人数超级多。我觉得大家喜欢,个方面是因为得简单,大家都能看得懂,个可扩展性还是非常强...

    贪吃蛇是个非常经典的游戏,用C语言来实现也是一个好玩的事情。这个游戏我写完后放在知乎,竟然点赞的人数超级多。我觉得大家喜欢,一个方面是因为写得简单,大家都能看得懂,一个可扩展性还是非常强的。

    我试了说一下这个代码 核心的三个函数

        menu();
        setup();
        draw();
    

    menu用来设置菜单,也就是我们一运行看到的那个。setup用来设置参数,我们需要设置高度和宽度,还有分数,食物的位置。draw也就是画,也就是画整个画面。

    还有一个枚举类型 这个结构体用来设置蛇的几个状态,我觉得这个也是面向对象编程的一个思想,把蛇的状态都封装成一个枚举类型。

    typedef enum
    {
            STOP = 0,
            LEFT,
            RIGHT,
            UP,
            DOWN
    }Direction;
    

    还有

    /*判断贪吃蛇的长度*/
    void logic()
    

    这个函数,这个函数应该是整个贪吃蛇的精髓了,要理解代码怎么把蛇给连接起来。用了点巧妙的东西。

    来看这里面的关键代码

    /*把上一个位置记下*/
        int lastX = tailX[0];
        int lastY = tailY[0];
        int last2X, last2Y;
        /*重新获取当前的位置*/
        tailX[0]=x;
        tailY[0]=y;
        int i=0;
        /*遍历整条蛇的长度 把 0 的位置空出来,其余蛇的位置往后面的空间移动*/
        for(i=1; i<ntail;i++)
        {
            last2X = tailX[i];
            last2Y = tailY[i];
            tailX[i]=lastX;
            tailY[i]=lastY;
            lastX = last2X;
            lastY = last2Y;
        }
    

    lastX lastY 用来存上一次的蛇头的位置。后面的 for 循环,通过tail 蛇的长度,把蛇上个状态给保存到数组tailX tailY里面。

    完整代码

    
    #include <stdio.h>
    #include <stdlib.h>
    #include <stdbool.h>
    #include <Windows.h>
    #include <time.h>
    #include <conio.h> /*键盘输入获取*/
    
    bool gameOver;
    bool stop = false;
    bool hit = false;
    /*游戏的边框大小*/
    const int width = 50;
    const int height = 20;
    /*蛇的坐标,食物的坐标还有分数*/
    int x,y,fruitX,fruitY,score;
    /*蛇每个点的坐标*/
    int tailX[200],tailY[200];
    /*蛇的默认长度*/
    int ntail=3;
    
    typedef enum
    {
            STOP = 0,
            LEFT,
            RIGHT,
            UP,
            DOWN
    }Direction;
    
    Direction Dir;
    /*开始菜单*/
    void menu()
    {
        int a;
        printf("------------------------------------------------------------------\n");
        printf("|                              贪吃蛇游戏                        |\n");
        printf("|                              1) 新游戏                         |\n");
        printf("|                              2) 开始边界                       |\n");
        printf("|                              3) 退出游戏                       |\n");
        printf("------------------------------------------------------------------\n");
        printf("---->请输入你的选择:");
        scanf("%d", &a);
    }
    
    /*初始化状态*/
    void setup()
    {
        gameOver = false;
        /*根据当前时间设置“随机数种子”*/
        srand(time(NULL));
        Dir = STOP;
        
        /*贪吃蛇的位置,固定在中间*/
        x= width/2;
        y= height/2;
        /*食物的位置,位置是随机的*/
        fruitX = rand()%width;
        fruitY = rand()%height;
        score = 0;
    }
    /*绘制界面*/
    void draw()
    {
            if(stop == true)
            {
                    return;
            }
        system("cls");/*清除屏幕*/
        printf("分数:%d",score);
        printf("\n");
        
            /*第一行*/
        int i;
        for(i= 0 ;i<width+1;i++)
            {
            printf("-");
        }
        printf("\n");
        
        /*画中间的画面*/
        int p;
        for(p= 0 ;p<height;p++)/*高度*/
            {
            int q;
            for(q= 0 ;q<width;q++)/*宽度*/
                    {
                            /*第一行最后已给字符*/
                if(q==0 || q==width-1)
                            {
                    printf("|");
                }
                
                            if(p == fruitY && q == fruitX)/*食物的随机坐标*/
                            {
                    printf("O");
                }
                            else
                            {
                        int k=0;
                        bool print = false;
                        /*贪吃蛇的长度 默认长度是 3*/
                                            for(k=0;k<ntail;k++)
                                            {
                            if(tailX[k]==q && tailY[k]==p)
                                                    {
                                printf("*");
                                print = true;
                            }
                        }
                        /*如果这个位置打印了 * 就不要打印空格了*/
                        if(!print)
                                            {
                                                    printf(" ");
                                            }
                }
            }
            printf("\n");
        }
    
            /*最后一行*/
        int j;
        for(j= 0 ;j<width+1;j++)
            {
            printf("-");
        }
    
    }
    /*按键输入控制*/
    void input()
    {
        if(_kbhit())
            {
                    /*获取键盘的输入字符*/
            switch(_getch())
                    {
                case '4':
                case 75:/*左键*/
                    Dir = LEFT;
                    hit= true;
                    break;
                case '8':
                case 72:/*上键*/
                    Dir = UP;
                    hit= true;
                    break;
                case '6':
                case 77:/*右键*/
                    Dir = RIGHT;
                    hit= true;
                    break;
                case '2':
                case 80:/*向下键盘键 */
                    Dir = DOWN;
                    hit= true;
                    break;
                case 'x':
                case 27:/*ESE*/
                    gameOver = true;
                    break;
                case 32:/*空格 暂停键*/
                                    stop = !stop;
                                    break;
            }
        }
            else if(!hit && stop == false)/*如果没有改变方向*/
            {
            x++;
        }
    }
    /*判断贪吃蛇的长度*/
    void logic()
    {
            if(stop == true)
            {
                    return;
            }
            
            /*把上一个位置记下*/
        int lastX = tailX[0];
        int lastY = tailY[0];
        int last2X, last2Y;
        /*重新获取当前的位置*/
            tailX[0]=x;
        tailY[0]=y;
        int i=0;
        /*遍历整条蛇的长度 把 0 的位置空出来,其余蛇的位置往后面的空间移动*/
        for(i=1; i<ntail;i++)
            {
            last2X = tailX[i];
            last2Y = tailY[i];
            tailX[i]=lastX;
            tailY[i]=lastY;
            lastX = last2X;
            lastY = last2Y;
        }
        /*根据方向来改变x y 的值*/
        switch(Dir)
            {
            case UP:
                y--;
                break;
            case DOWN:
                y++;
                break;
            case LEFT:
                x--;
                break;
            case RIGHT:
                x++;
                break;
        }
        if(x<0 || width<x || y<0 || height<y)
            {
            gameOver = true;
            /*清除屏幕*/
            system("cls");
            printf("------------------------------------------------------------------\n");
                printf("|                                                                |\n");
                printf("|                                                                |\n");
                printf("|                             游戏结束                           |\n");
                printf("|                                                                |\n");
                printf("|                                                                |\n");
                printf("------------------------------------------------------------------\n");
        }
        if(x==fruitX && y==fruitY)
            {
                    /*吃了一个食物,蛇的长度增加1*/
            ntail++;
            score+=10;
            /*更新下一个食物的位置*/
            fruitX = rand()%width;
            fruitY = rand()%height;
        }
    }
    int main()
    {
    #if 0
            while(1)
            {
                    printf("%d\n",_getch());
            }
    #endif
        menu();
        setup();
        draw();
        /*循环画贪吃蛇的界面*/
            while(!gameOver)
            {
            draw();
            input();
            logic();
            Sleep(70);
        }
    
        return 0;
    }
    

    上面这段代码直接在Dev C++上面应该是可以运行的,很多人在知乎上私信问我,为什么我的贪吃蛇执行不了呢,可能就是平台不同,少了这个头文件,少了那个头文件,但是你为什么不能跟我一样,用Dev C++呢,轻量级,简单。代码的精髓是什么?我认为精髓一定是思想,不是你写了多少行代码,用了什么高端的IDE。

    我自认为我的注释已经写得不错了,所以就没有什么好说明的了吧,有不明白的把代码过一下,至于屏幕刷新这个东西,如果只是用时间刷新就会闪屏,所以出现了一个双缓存,把要显示的东西送到一个buff里面去,另一个buff用来显示,这样就可以保证不会出现闪屏。除了写贪吃蛇,可以用这个方法写其他小程序,挺有意思的。

    在知乎上,发起了一个C语言 100 行代码之内实现贪吃蛇的问题。我觉得很不错,里面很多同学的回复都非常赞,特别是叶大神的回复。

    https://www.zhihu.com/question/360814879/answer/1013986215


    扫码或长按关注

    回复「 篮球的大肚子」进入技术群聊

    展开全文
  • 步步教你怎么用python贪吃蛇游戏

    万次阅读 多人点赞 2019-06-27 18:17:52
    目录 0 引言 1 环境 2 需求分析 ...前几天,星球有人提到贪吃蛇,下子就勾起了我的兴趣,毕竟在那个Nokia称霸的年代,这款游戏可是经典中的经典啊!而用Python(蛇)玩Snake(贪吃蛇),那再合适不过了

    目录
    0 引言
    1 环境
    2 需求分析
    3 代码实现
    4 后记

    0 引言

    前几天,星球有人提到贪吃蛇,一下子就勾起了我的兴趣,毕竟在那个Nokia称霸的年代,这款游戏可是经典中的经典啊!而用Python(蛇)玩Snake(贪吃蛇),那再合适不过了???

    先通过下面这个效果图来感受下吧!
    在这里插入图片描述

    1 环境

    操作系统:Windows

    Python版本:3.7.3

    2 需求分析

    我们先来回顾下贪吃蛇中的游戏元素及游戏规则。

    首先呢,需要有贪吃蛇、有食物;需要能控制贪吃蛇来上下移动获取食物;贪吃蛇在吃取食物后,自身长度增加,同时食物消失并随机生成新的食物;如果贪吃蛇触碰到四周墙壁或是触碰到自己身体时,则游戏结束。

    游戏规则就是这么简单,接下来我们借助一个第三方库pygame来实现它。

    Pygame是一个利用SDL库的游戏库, 是一组用来开发游戏软件的 Python 程序模块。

    SDL(Simple DirectMedia Layer)是一个跨平台库,支持访问计算机多媒体硬件(声音、视频、输入等),SDL非常强大,但美中不足的是它是基于 C 语言的。

    PyGame是 SDL 库的 Python 包装器(wrapper),Pygame 在SDL库的基础上提供了各种接口,从而使用用户能够使用python语言创建各种各样的游戏或多媒体程序。

    它的安装方法很简单,如下:

    pip install pygame

    想要了解更多pygame功能的朋友也可以查阅官方的文档。

    3 代码实现

    首先导入我们要用到的模块,除了第三方库pygame外,我们还会用到一些Python内置的模块如sys、random、time等,一并导入即可。

    import pygame, sys, random, time
    # 从pygame模块导入常用的函数和常量
    from pygame.locals import *   
    

    3.1 一些全局参数的初始化

    接下来,我们需要声明一些全局参数。如初始化pygame、定义游戏窗口的大小、窗口的标题、定义全局的颜色变量等信息。

    # 初始化Pygame库
    pygame.init()
    # 初始化一个游戏界面窗口
    DISPLAY = pygame.display.set_mode((640, 480))
    # 设置游戏窗口的标题
    pygame.display.set_caption('人人都是Pythonista - Snake')
    # 定义一个变量来控制游戏速度
    FPSCLOCK = pygame.time.Clock()
    # 初始化游戏界面内使用的字体
    BASICFONT = pygame.font.SysFont("SIMYOU.TTF", 80)
    
    # 定义颜色变量
    BLACK = pygame.Color(0, 0, 0)
    WHITE = pygame.Color(255, 255, 255)
    RED = pygame.Color(255, 0, 0)
    GREY = pygame.Color(150, 150, 150)
    

    3.2 初始化贪吃蛇及食物

    游戏中需要有贪吃蛇及食物,我们给定一个初始值。我们将整个界面看成许多20*20的小方块,每个小方块代表一个标准小格子,贪吃蛇的长度就可以用几个标准小格子表示。我们将贪吃蛇身体用列表的形式存储,方便之后的删减。
    ‘’‘初始化贪吃蛇及食物’’’

    # 贪吃蛇的的初始位置
    snake_Head = [100,100]
    # 初始化贪吃蛇的长度 (注:这里以20*20为一个标准小格子)
    snake_Body = [[80,100],[60,100],[40,100]]
    # 指定蛇初始前进的方向,向右
    direction = "right"
    
    # 给定第一枚食物的位置
    food_Position = [300,300]
    # 食物标记:0代表食物已被吃掉;1代表未被吃掉。
    food_flag = 1
    

    3.3 实现贪吃蛇的上下左右移动

    我们需要控制贪吃蛇的上下左右的移动,这里通过监听键盘输入来实现。利用键盘中的上下左右键或WASD键来控制贪吃蛇的运动。

    # 检测按键等Pygame事件
    for event in pygame.event.get():
        if event.type == QUIT:
            # 接收到退出事件后,退出程序
            pygame.quit()
            sys.exit()
            
        # 判断键盘事件,用 方向键 或 wsad 来表示上下左右
        elif event.type == KEYDOWN:
            if (event.key == K_UP or event.key == K_w) and direction != DOWN:
                direction = UP
            if (event.key == K_DOWN or event.key == K_s) and direction != UP:
                direction = DOWN
            if (event.key == K_LEFT or event.key == K_a) and direction != RIGHT:
                direction = LEFT
            if (event.key == K_RIGHT or event.key == K_d) and direction != LEFT:
                direction = RIGHT
    

    接下来就是将蛇前进方向按照键盘的输入进行转弯操作,并将蛇的头部当前的位置加入到蛇身的列表中。

    # 根据键盘的输入,改变蛇的头部,进行转弯操作
    if direction == LEFT:
        snake_Head[0] -= 20
    if direction == RIGHT:
        snake_Head[0] += 20
    if direction == UP:
        snake_Head[1] -= 20
    if direction == DOWN:
        snake_Head[1] += 20
    
    # 将蛇的头部当前的位置加入到蛇身的列表中
    snake_Body.insert(0, list(snake_Head))
    

    3.4 判断是否吃到食物

    如果蛇头与食物的位置重合,则判定吃到食物,将食物数量清零;而没吃到食物的话,蛇身就会跟着蛇头运动,蛇身的最后一节将被踢出列表。

    # 判断是否吃掉食物
    if snake_Head[0]==food_Position[0] and snake_Head[1]==food_Position[1]:
        food_flag = 0
    else:
        snake_Body.pop()
    

    3.5 重新生成食物

    当游戏界面中的食物数量为0时,需要重新生成食物。利用random函数来生成随机位置

    # 生成新的食物
    if food_flag == 0:
        # 随机生成x, y
        x = random.randrange(1,32)
        y = random.randrange(1,24)
        food_Position = [int(x*20),int(y*20)]
        food_flag = 1
    

    3.6 绘制贪吃蛇、食物、分数等信息

    定义贪吃蛇的绘制函数

    # 绘制贪吃蛇
    def drawSnake(snake_Body):
        for i in snake_Body:
            pygame.draw.rect(DISPLAY, WHITE, Rect(i[0], i[1], 20, 20))
    
    定义食物的绘制函数
    # 绘制食物的位置
    def drawFood(food_Position):
        pygame.draw.rect(DISPLAY, RED, Rect(food_Position[0], food_Position[1], 20, 20))
    
    定义分数的绘制函数
    # 打印出当前得分
    def drawScore(score):
        # 设置分数的显示颜色
        score_Surf = BASICFONT.render('%s' %(score), True, GREY)
        # 设置分数的位置
        score_Rect = score_Surf.get_rect()
        score_Rect.midtop = (320, 240)
        # 绑定以上设置到句柄
        DISPLAY.blit(score_Surf, score_Rect)
    

    这些都定义好之后,我们需要在游戏主逻辑中调用它们,并刷新Pygame的显示层,贪吃蛇与食物的每一次移动,都会进行刷新显示层的操作来显示。最后我们可以设定一个速度值来合理控制游戏执行的速度。

    DISPLAY.fill(BLACK)
    # 画出贪吃蛇
    drawSnake(snake_Body)
    # 画出食物的位置
    drawFood(food_Position)
    # 打印出玩家的分数
    drawScore(len(snake_Body) - 3)
    # 刷新Pygame的显示层,贪吃蛇与食物的每一次移动,都会进行刷新显示层的操作来显示。
    pygame.display.flip()
    # 控制游戏速度
    FPSCLOCK.tick(7)
    

    3.7 定义游戏结束的画面并判断游戏是否结束

    定义函数,用于展示游戏结束的画面并退出程序

    # 游戏结束并退出
    def GameOver():
        # 设置GameOver的显示颜色
        GameOver_Surf = BASICFONT.render('Game Over!', True, GREY)
        # 设置GameOver的位置
        GameOver_Rect = GameOver_Surf.get_rect()
        GameOver_Rect.midtop = (320, 10)
        # 绑定以上设置到句柄
        DISPLAY.blit(GameOver_Surf, GameOver_Rect)
    
        pygame.display.flip()
        # 等待3秒
        time.sleep(3)
        # 退出游戏
        pygame.quit()
        # 退出程序
        sys.exit()
    

    在游戏主逻辑中加入判断,游戏是否结束

    '''游戏结束的判断'''
    # 贪吃蛇触碰到边界
    if snake_Head[0]<0 or snake_Head[0]>620:
        GameOver()
    if snake_Head[1]<0 or snake_Head[1]>460:
        GameOver()
    # 贪吃蛇触碰到自己
    for i in snake_Body[1:]:
        if snake_Head[0]==i[0] and snake_Head[1]==i[1]:
            GameOver()
    

    4 后记

    本文利用Pygame模块实现了最简单的贪吃蛇版本。当然还有很多需要优化的地方,比如随机生成食物时如何避免出现在贪吃蛇的自身上、通过贪吃蛇的长度来自动控制游戏速度等等。更高级一点的有如何通过AI自动玩贪吃蛇、贪吃蛇的双人对战等,期待大家利用Python可以把贪吃蛇玩出一个新的高度!???

    公众号「Python专栏」后台回复关键字「贪吃蛇」获取本文全套完整代码!

    展开全文
  • 用Java写一个五子棋小游戏

    万次阅读 多人点赞 2018-07-07 09:30:24
    棋盘是15*15(可以自己规定)游戏规则:(1)对局双方各执色棋子。(2)空棋盘开局。(3)黑先、白后,交替下子,每次只能下子。(4)棋子下在棋盘的空白点上,棋子下定后,不得向其它点移动,不得棋盘上拿掉或拿起另...

    棋盘是15*15(可以自己规定)

    游戏规则:

    (1)对局双方各执一色棋子。
    (2)空棋盘开局。
    (3)黑先、白后,交替下子,每次只能下一子。
    (4)棋子下在棋盘的空白点上,棋子下定后,不得向其它点移动,不得从棋盘上拿掉或拿起另落别处。
    (5)黑方的第一枚棋子可下在棋盘任意交叉点上。
    (6)任意一方达成五连子即可获胜

    Java开发用到了Swing轻量级组件用来处理游戏界面,判断胜利的逻辑代码是核心。

    1.整体的设计

    public class MyJpanel extends JFrame {
    	PicJpanel pj;
    
    	public MyJpanel() {
    		init();
    	}
    
    	private void init() {
    		// 逻辑代码处理部分
    	}
    
    	public static void main(String[] args) {
    		new MyJpanel();
    	}
    }
    
    class PicJpanel extends JPanel {
    	MyJpanel mj;
    
    	public PicJpanel(MyJpanel mj) {
    		// 设定面板在窗体中的位置以及高度和宽度
    		this.setBounds(0, 0, mj.getWidth(), mj.getHeight());
    		this.mj = mj;
    	}
    
    	/**
    	 * 画组件
    	 */
    	@Override
    	protected void paintComponent(Graphics g) {
    
    		// 设置一个背景
    		try {
    			BufferedImage bi = ImageIO.read(new File("img/bj.jpg"));
    			g.drawImage(bi, 0, 0, this);
    		} catch (IOException e) {
    			e.printStackTrace();
    		}
    
    	}
    
    class MyMouse extends MouseAdapter {
    	MyJpanel mj;
    
    	public MyMouse(MyJpanel mj) {
    		super();
    		this.mj = mj;
    	}
    
    	@Override
    	public void mousePressed(MouseEvent e) {	
    		//点击事件的处理
    	}
    
    }
    

    MyJpanel 继承Jfram作为整体的一个框架,PicJpanel继承JPanel描绘图画,两者是通过双向关联来互相取值的.MyMouse用来处理点击时间(也是双向关联Jfram)。

    2.整体设计模式确定后,就是画图了

    在MyJpanel的Init()方法里设置大小,布局方式等,在PicJanel里的paintComponent(Graphics g)方法里通过画图工具画出棋盘。

    画图的思路是通过循环画一个15*15的格子。

    init()和paintComponent(Graphics g)里的代码:

    private void init() {
    		// 窗体的常用设置
    				this.setSize(750, 780);// 设置窗体的大小,宽度和高度,单位是像素
    				this.setDefaultCloseOperation(this.EXIT_ON_CLOSE);// 设置窗体关闭时主线程自动关闭
    				this.setLocationRelativeTo(null);// 设置窗体出现的位置在显示器正中间
    				this.setResizable(false);// 设置窗体固定大小
    				this.setLayout(null);// 不启用布局管理器,改为手动布局
    				this.setTitle("画图");
    
    
    				// 添加面板到窗体
    
    
    				pj = new PicJpanel(this);
    				this.add(pj);
    
    
    				this.setVisible(true);
    	}
    
    protected void paintComponent(Graphics g) {
    
    		// 设置一个背景
    		try {
    			BufferedImage bi = ImageIO.read(new File("img/bj.jpg"));
    			g.drawImage(bi, 0, 0, this);
    		} catch (IOException e) {
    			e.printStackTrace();
    		}
    
    		g.setColor(Color.BLACK);
    		//通过循环画格子
    		for (int i = 0; i < 15; i++) {
    			for (int j = 0; j < 15; j++) {
    				g.drawRect(50 * i, 50 * j, 50, 50);
    				
    			}
    		}
    	}

    画好之后就是这样


    3.接着添加点击事件

    要求

    1.精确点击

    2.首先落子的是黑棋

    2.每次一方下完棋子颜色改变

    说一下思路,我这里是750*750的,行和列都是15,这样就很容易获取x和y的值(通过鼠标点击事件getX和getY再除以50则可得到x,y),说到x,y大家肯定想到要使用二维数组,每错,我们在前台看到的是棋盘,但是实际存储值的地方在二维数组,所以要定义一个二维数组map[15][15]。每次获取到x和y则将map[x][y]=1或2(黑子或白子),每次点击之后都要调用repaint()方法重新绘制图画。看看MyMouse里的mousePressed()方法。

    在这之前先在MyJpanel里设置2个全局变量

            int map[][] = new int[15][15]; // 棋盘

    int flag = 2; // 1为白 2为黑 黑白交替默认为黑

    由于MyMouse 关联了MyJpanel 所以可以获取到MyJpanel 的值

    public void mousePressed(MouseEvent e) {	
    			Point p = e.getPoint();// 获取鼠标点下的位置的坐标
    			// 点击之后map值发生改变
    			int x = (int) p.getX() / (750 / 15);
    			int y = (int) p.getY() / (750 / 15);
    			System.out.println("x=" + p.getX() + "   y=" + p.getY());
    			System.out.println("x=" + x + "   y=" + y);
    			
    			// 改变棋子的颜色
    			if (map[y][x] == 0) {
    				map[y][x] = mj.flag;
    			}
    			
    			// 改变顺序
    			if (mj.flag == 1) {
    				mj.flag = 2;
    			} else if(mj.flag==2){
    				mj.flag = 1;
    			}
    			//重置绘图
    			mj.pj.repaint();
    			
    	}
    做完点击事件处理后,要回到图像处理部分PicJpanel在循环里添加一行代码如下:
    for (int i = 0; i < 15; i++) {
    			for (int j = 0; j < 15; j++) {
    				g.drawRect(50 * i, 50 * j, 50, 50);
    				// 1为白
    				if (map[i][j] == 1) {
    					g.setColor(Color.WHITE);
    					g.fillOval(50 * j, 50 * i, 50, 50);
    				}
    				g.setColor(Color.black);
    				// 2为黑
    				if (map[i][j] == 2) {
    					g.setColor(Color.black);
    					g.fillOval(50 * j, 50 * i, 50, 50);
    				}
    			}

    看看效果



    点击第一行一列后台处理之后输出结果。嗯差不多做了一大半了。剩下来的就是核心部分了

    4.胜负判断

    每次调用鼠标点击时间都要判断一次输赢。

    讲一下思路。要判断输赢。要判断每次落子的地方该子的四个大方向是否有五颗连续的子,4个大方向为上下,左右,左斜,右斜,想一下米子的写法就可以了。同方向上是否有五颗颜色一样的棋子,实际上就是连续问题,这里有很多处理方法。博主给出的不是最佳方案。

    4步完成后稍微修改处理一下代码就可以了。

    博主的代码如下,这个小游戏主要是画图和数组两个部分的内容,基础稍好的同学可以试着自己实现一下,可以参照博主的设计思路,细节上可以自己处理。不懂的可以留言

    import java.awt.Color;
    import java.awt.Graphics;
    import java.awt.Point;
    import java.awt.event.MouseAdapter;
    import java.awt.event.MouseEvent;
    import java.awt.event.MouseListener;
    import java.awt.image.BufferedImage;
    import java.io.File;
    import java.io.IOException;
    
    import javax.imageio.ImageIO;
    import javax.swing.JFrame;
    import javax.swing.JOptionPane;
    import javax.swing.JPanel;
    
    public class MyJpanel extends JFrame {
    	PicJpanel pj;
    	int map[][] = new int[16][16]; // 棋盘
    	int flag = 2; // 1为白 2为黑 黑白交替默认为黑
    	int winer=0; //规定赢者
    
    	public int[][] getMap() {
    		return map;
    	}
    
    	public void setMap(int[][] map) {
    		this.map = map;
    	}
    
    	public MyJpanel() {
    		init();
    	}
    
    	private void init() {
    		// 窗体的常用设置
    		this.setSize(750, 780);// 设置窗体的大小,宽度和高度,单位是像素
    		this.setDefaultCloseOperation(this.EXIT_ON_CLOSE);// 设置窗体关闭时主线程自动关闭
    		this.setLocationRelativeTo(null);// 设置窗体出现的位置在显示器正中间
    		this.setResizable(false);// 设置窗体固定大小
    		this.setLayout(null);// 不启用布局管理器,改为手动布局
    		this.setTitle("画图");
    
    		// 添加面板到窗体
    
    		pj = new PicJpanel(this);
    		pj.addMouseListener(new MyMouse(this));// 给面板添加一个鼠标监听事件
    		this.add(pj);
    
    		this.setVisible(true);
    	}
    
    	public static void main(String[] args) {
    		new MyJpanel();
    	}
    }
    
    class PicJpanel extends JPanel {
    	MyJpanel mj;
    
    	public PicJpanel(MyJpanel mj) {
    		// 设定面板在窗体中的位置以及高度和宽度
    		this.setBounds(0, 0, mj.getWidth(), mj.getHeight());
    		this.mj = mj;
    	}
    
    	/**
    	 * 画组件
    	 */
    	@Override
    	protected void paintComponent(Graphics g) {
    
    		try {
    			BufferedImage bi = ImageIO.read(new File("img/bj.jpg"));
    			g.drawImage(bi, 0, 0, this);
    		} catch (IOException e) {
    			e.printStackTrace();
    		}
    
    		int map[][] = mj.map;
    
    		g.setColor(Color.BLACK);
    		
    		for (int i = 0; i < 15; i++) {
    			for (int j = 0; j < 15; j++) {
    				g.drawRect(50 * i, 50 * j, 50, 50);
    				// 1为白
    				if (map[i][j] == 1) {
    					g.setColor(Color.WHITE);
    					g.fillOval(50 * j, 50 * i, 50, 50);
    				}
    				g.setColor(Color.black);
    				// 2为黑
    				if (map[i][j] == 2) {
    					g.setColor(Color.black);
    					g.fillOval(50 * j, 50 * i, 50, 50);
    				}
    			}
    		}
    		
    		
    		// g.setColor(Color.RED);//设置画笔为红色
    		// g.drawRect(50, 50, 100, 100);//画一个矩形.前面两个参数决定位置,后两个参数决定大小
    		// g.setColor(Color.BLUE);
    		// g.fillRect(200,50, 100, 100);//画一个实心的矩形
    		// g.drawOval(50, 200, 100, 100);
    		// g.fillOval(200, 200, 100, 100);
    	}
    
    }
    
    class MyMouse extends MouseAdapter {
    	MyJpanel mj;
    
    	public MyMouse(MyJpanel mj) {
    		super();
    		this.mj = mj;
    	}
    
    	@Override
    	public void mousePressed(MouseEvent e) {
    		
    		//重置1
    		if(mj.winer!=0){
    			mj.setMap(new int[16][16]);
    			mj.winer=0;
    			mj.pj.repaint();
    			return;
    		}
    		int map[][] = mj.map;
    		Point p = e.getPoint();// 获取鼠标点下的位置的坐标
    		// 点击之后map值发生改变
    		int x = (int) p.getX() / (750 / 15);
    		int y = (int) p.getY() / (750 / 15);
    		System.out.println("x=" + p.getX() + "   y=" + p.getY());
    		System.out.println("x=" + x + "   y=" + y);
    
    		// 改变棋子的颜色
    		if (map[y][x] == 0) {
    			map[y][x] = mj.flag;
    		}
    		
    		// 改变顺序
    		if (mj.flag == 1) {
    			mj.flag = 2;
    		} else if(mj.flag==2){
    			mj.flag = 1;
    		}
    
    
    		//判断输赢
    		MyMouse mouse=new MyMouse(mj);
    		if(mouse.isWin(y, x, map)){
    			if(map[y][x]==1){
    				mj.winer=1;
    				mj.pj.repaint();
    				//弹出获胜信息
    				JOptionPane.showMessageDialog(mj, "白子胜");
    				//重置棋子颜色为黑棋
    				mj.flag=2;
    			}
    			if(map[y][x]==2){
    				mj.winer=2;
    				mj.pj.repaint();
    				JOptionPane.showMessageDialog(mj, "黑子胜");
    				//重置棋子颜色为黑棋
    				mj.flag=2;
    			}
    		}
    		
    		//先调整数组 在绘图
    		mj.setMap(map);
    		mj.pj.repaint();
    		
    				
    		
    	}
    
    	public boolean isWin(int x, int y, int map[][]) {
    		// 对胜负判断
    		// 4个方向 左右 上下 左斜 右斜
    		// 对一个棋子的一个方向的10颗棋子进行判断 是否满足5子连续
    		// 左右
    		
    		int num = 1;
    		for (int i = 0; i < 14; i++) {
    			if (map[x][i] != 0) {
    				if (map[x][i] == map[x][i + 1]) {
    					num++;
    					if (num >= 5) {
    						System.out.println("win");
    						return true;
    					}
    				} else {
    					num = 1;
    				}
    			}
    		}
    
    		// 上下
    		num = 1;
    		for (int i = 0; i < 14; i++) {
    			if (map[i][y] != 0) {
    				if (map[i][y] == map[i + 1][y]) {
    					num++;
    					if (num >= 5) {
    						System.out.println("win");
    						return true;
    					}
    				} else {
    					num = 1;
    				}
    			}
    		}
    
    		num=1;
    		// 右斜 x-1 j+1
    		for (int i = 0; i < map.length*2-1; i++) {
    			for (int j = 1; j < map.length ; j++) {
    				if (((i - j) >= 0) && ((i - j) < map.length)) {
    					if(map[j][i-j]!=0){
    						if(map[j][i-j]==map[j-1][i-j+1]){
    							num++;
    							if (num >= 5) {
    								System.out.println("win");
    								return true;
    							}
    						}else{
    							num=1;
    						}
    					}
    				}
    			}
    		}
    		
    		num=1;
    		//左斜 x+1 y+1
    		for (int i = -map.length; i < map.length; i++) {
    			for (int j = 1; j < map.length; j++) {
    				if(((i+j)>=0)&&((i+j)<map.length)){
    					if(map[j][j+i]!=0){
    						if(map[j][i+j]==map[j+1][i+j+1]){
    							num++;
    							if (num >= 5) {
    								System.out.println("win");
    								return true;
    							}
    						}else{
    							num=1;
    						}
    					}
    				}
    			}
    		}
    		
    		return false;
    	}
    
    }
    展开全文
  • 写一个猜数字的游戏

    千次阅读 2021-04-06 21:48:25
    写一个猜数字的游戏 猜数字游戏: 1、电脑会生成个随机数 2、猜数字 首先明白游戏的玩法:在一定数值范围内,游戏随机生成个数字,玩家输入比随机数大的数字时,程序会提醒,数值大于目标数,反之亦然。通过...

    写一个猜数字的游戏

    猜数字游戏:
    1、电脑会生成一个随机数
    2、猜数字

    首先明白游戏的玩法:在一定数值范围内,游戏随机生成一个数字,玩家输入比随机数大的数字时,程序会提醒,数值大于目标数,反之亦然。通过不断试错,最终找出目标数字。此游戏可以重复玩。

    第一步:设立菜单(输出1进行游戏,0退出游戏)

    设立一个menu(),菜单函数

    void menu()
    {
    
     printf("*******************************************\n");
     printf("************  1. play 0. exit  ************\n");
     printf("*******************************************\n");
    }
    

    因为游戏可以重复玩,所以需要一次执行,再进行循环。选择do…while()语句

    #include <stdio.h>
    void menu()
    {
    
     printf("*******************************************\n");
     printf("************  1. play 0. exit  ************\n");
     printf("*******************************************\n");
    }
    int main()
    {   
    	int input = 0;
      do
      {
           menu();
    	   printf("请选择>:");
           scanf("%d", &input);
           switch(input)
    	   {
    	   case 1:
    		   game();
    		   break;
    	   case 0:
    		   printf("退出游戏\n");
    		   break;
    	   default:
    		   printf("选择错误\n");
    		   break;
    	   }
    	
     }
      while(input)
    	  ;
    
      return 0;
    }
    

    第二步:生成随机数

    int rand(void) :返回一个范围在 0 到 RAND_MAX 之间的伪随机数。

    RAND_MAX 是一个常量,它的默认值在不同的实现中会有所不同,但是值至少是 32767。
    使用该函数,需要引头文件<stdib.h>

    srand 函数是随机数发生器的初始化函数。
    它初始化随机种子,会提供一个种子,这个种子会对应一个随机数,如果使用相同的种子后面的 rand() 函数会出现一样的随机数,如: srand(1); 直接使用 1 来初始化种子。不过为了防止随机数每次重复,常常使用系统时间来初始化,即使用 time函数来获得系统时间,它的返回值为从 00:00:00 GMT, January 1, 1970 到现在所持续的秒数,然后将time_t型数据转化为(unsigned)型再传给srand函数,即: srand((unsigned) time(&t)); 还有一个经常用法,不需要定义time_t型t变量,即: srand((unsigned) time(NULL)); 直接传入一个空指针,因为你的程序中往往并不需要经过参数获
    得的数据。
    需要引用头文件<time.hw>

    void game()
    { 
      int ret = 0;
      srand((unsigned int)time(NULL));
      ret =rand();
      printf("%d\n", ret);
      printf("猜数字游戏\n");
    }
     
    

    在这里插入图片描述
    此时生成了随机数,但是如果输入数字的时间过快,可能会输出相同的数字,而且是递增的。
    所以srand((unsigned int)time(NULL))位置需要调整到主函数内。即:

    int main()
    {   
    	int input = 0;
    	srand((unsigned int)time(NULL));
    	.....
    

    在这里插入图片描述
    解决了生成随机数的问题,但是rand()函数生成的数字是0到32767,对于猜数字游戏来说,范围太大。将范围调整成1~100。
    想要输出给定范围之内的随机数,需要使用rand() % (b - a + 1)+ a,显然,rand()% (b - a + 1)的范围是[0,b - a],再加上a之后的范围就是[a,b]下面的代码是生成[0,2]和[3,8]范围内的随机数。

    void game()
    { 
      int ret = 0;
      
      ret =rand()%100+1;
      printf("%d\n", ret);
      printf("猜数字游戏\n");
    }
    

    第三步:进行数字判断

      while(1)
      {
        printf("请猜数字:>");
    	scanf("%d",&guess);
    	if(guess>ret)
    	{
    	  printf("猜大了\n");
        }
    	else if(guess<ret)
    	{
    	  printf("猜小了\n");
    	}
    	else
    	{
    	  printf("猜对了\n");
    	  break;
    	}
      }
    }
    
    

    最终效果

    #define _CRT_SECURE_NO_WARNINGS
    
    #include <stdio.h>
    #include<stdlib.h>
    #include<time.h>
    void game()
    { 
      int guess = 0;
      int ret = 0;
      ret =rand()%100+1;
      while(1)
      {
        printf("请猜数字:>");
    	scanf("%d",&guess);
    	if(guess>ret)
    	{
    	  printf("猜大了\n");
        }
    	else if(guess<ret)
    	{
    	  printf("猜小了\n");
    	}
    	else
    	{
    	  printf("猜对了\n");
    	  break;
    	}
      }
    }
    
     
    void menu()
    {
    
     printf("*******************************************\n");
     printf("************  1. play 0. exit  ************\n");
     printf("*******************************************\n");
    }
    int main()
    {   
    	int input = 0;
    	srand((unsigned int)time(NULL));
      do
      {
           menu();
    	   printf("请选择>:");
           scanf("%d", &input);
           switch(input)
    	   {
    	   case 1:
    		   game();
    		   break;
    	   case 0:
    		   printf("退出游戏\n");
    		   break;
    	   default:
    		   printf("选择错误\n");
    		   break;
    	   }
    	
       }while(input);
    	  
    
      return 0;
    }
    
    

    在这里插入图片描述


    在整个代码编写过程中,最复杂的就是随机值的生成。要明白srand()和rand()函数的使用。
    计算机并不能产生真正的随机数,而是已经编写好的一些无规则排列的数字存储在电脑里,把这些数字划分为若干相等的N份,并为每份加上一个编号用srand()函数获取这个编号,然后rand()就按顺序获取这些数字,当srand()的参数值固定的时候,rand()获得的数也是固定的,所以一般srand的参数用time(NULL),因为系统的时间一直在变,所以rand()获得的数,也就一直在变,相当于是随机数了。只要用户或第三方不设置随机种子,那么在默认情况下随机种子来自系统时钟。如果想在一个程序中生成随机数序列,需要至多在生成随机数之前设置一次随机种子。

    即:只需在主程序开始处调用 srand((unsigned int)time(NULL)); 后面直接用rand就可以了。不要在 for 等循环放置。
    srand()函数描述
    rand()函数描述

    展开全文
  • 所以给form1声明三个字段,种更理想的情况是只定义个Actor的列表,然后不管是什么物件,往这个列表里塞就好,在更复杂的游戏中采用那种处理方式也的确是更好的选择。 /// /// 场景中所有砖块的列表 /// ...
  • 目录人人都能写游戏系列()创建项目布置场景添加物体调整物体添加材质球制作预制体预制体是什么为什么要使用预制体制作预制体编写脚本事先准备开始编写脚本Start方法Update方法跳哪了?摄像机和plane的跟随完整...
  • 自己开发的第个android 游戏《是男人就下100层》,注意是安卓游戏,不是IPhone的。截图如下:   这个有游戏是用重力感应来控制的,所以要晃动手机来控制人物移动。这个游戏的目标是下越多层数越好。这个...
  • 【Python】01:从头开始打砖块小游戏~(

    千次阅读 多人点赞 2020-07-19 16:54:52
    Hi~ o( ̄▽ ̄)ブ 我又双叒叕来啦~ 等你很久啦~NOTE:楼主11岁女学生,文笔(排版风格)不好别介意啦~NOTE2:这个游戏是我从头开始的,所以会比较慢,就相当于检测一下这个疫情期间的学习成果吧~ 关于这个游戏: ...
  • Java的第个小游戏

    万次阅读 多人点赞 2020-11-10 15:25:31
    步:发现类(对象) 人物-小丑(敌方-友方): 子弹-帽子: 墙体: 爆炸物: 第二步:发现属性 小丑: 宽高 , 位置(x y), 移动速度 帽子: 宽高 , 位置(x y), 移动速度 墙体: 宽高 , 位置(x y) 爆炸物:宽高 , 位置(x y) 第三...
  • 用原生js+html写一个像素鸟游戏

    万次阅读 多人点赞 2019-12-09 17:41:19
    前言: 用html+js+css写一个面向对象板的像素鸟游戏 看一下效果把: 看一下全部的代码把: HTML代码 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <...
  • 个C语言的小游戏(flappy bird)

    千次阅读 2017-03-14 17:34:40
    从中获取的许多知识,本文中的游戏也是里面学的,不过本人又自己加了一些功能。 这是类似于手机上曾经热门的个手机游戏,本人能力有限这两天还没搞出图像库的文件,下次争取做个图形交互的小游戏。 这个...
  • 用js卡牌游戏

    千次阅读 2019-06-26 17:44:00
    用js卡牌游戏) 不想看废话的点这 直接看代码的点这 废话(前言) 现在游戏多了,不过总是感觉不太对自己的口味,每个游戏都感觉和自己想象中的要差了那么点点,所以我决定尝试着自己写一个...
  • VC写一个荣光医院修补弹坑游戏助手

    千次阅读 2009-12-18 01:13:00
    可惜技艺不精,级数较低,刚中央区,人就被拉的惨不忍睹,有些还能回拉,遇到有些高级玩家,回拉,竟然赏我了两个弹坑,实在影响医院美观.据说弹坑只有两个办法修补,个是花钱买道具修补,个是玩修补弹坑游戏过关也能...
  • 写一个简单猜数字游戏的小程序

    千次阅读 2016-10-25 11:22:56
    需求:1、要求随机生成个整数,由用户输入猜测的数字,猜测正确则游戏结束,错误则分数减10分,猜测次数自增1.当分数减为0时,提示用户是否充值,用户充值则游戏继续,重新生成随机数字,总分和答题次数重置.,...
  • 小白2048小游戏速成教程(python不到100行)

    万次阅读 多人点赞 2018-08-14 13:05:07
    2048游戏共有16个格子,初始时会有两个格子上安放了两个数字2,每次可以选择上下左右其中个方向去滑动,每滑动次,所有的数字方块都会往滑动的方向靠拢外,系统也会在空白的地方随即出现个数字方块,相同数字...
  • 用python写一个简单的弹球游戏

    千次阅读 2018-01-14 18:33:43
    用python写一个简单的弹球游戏,可以使用球拍接住球让球在边框内不停的弹动,如果球拍没有接住则游戏结束 我们需要导入tkinter模块来创建画布 ,导入时间模块来控制球的速度,就是控制球移动的间隔时间 ,导入随机...
  • 100 行代码写一个图片验证码组件

    千次阅读 多人点赞 2021-03-02 15:10:46
    验证码(Captcha)的作用是防止别有用心的人通过编写“自动注册机”这类手段来大量发送非法的请求。这类请求通常涉及数据库的操作,因此...典型的种方法就是图片验证码,如下图所示是个加入干扰码的数字验证图片
  • h5游戏开发:用html+css+js写一个整蛊游戏

    千次阅读 多人点赞 2020-04-13 14:31:48
    有玩家看到这个标题可能第反应是什么恐怖游戏,或者有奇怪的东西在终点等着他,为了消除这种顾虑,我们将游戏设定改一下,设计为通过摇骰子的方式决定玩家走的步数,而不是玩家自己走。这样我们就拥有进一步控...
  • 用Java写一个简单的回合制游戏

    千次阅读 2020-10-29 07:55:25
    用Java写一个简单的回合制游戏 创建基本属性,血量,名字,技能,技能伤害。 如下: public class One3 { //创建三个属性 private String name; private String[] skill; private long[] skillharm; ...
  • Java 用java GUI写一个贪吃蛇小游戏

    千次阅读 2020-12-05 13:07:46
    目录主要用到 swing 包下的一些类上代码游戏启动类游戏数据类游戏面板类代码地址 主要用到 swing 包下的一些类 JFrame 窗口类 JPanel 面板类 KeyListener 键盘接口 ActionListener 监听接口 上代码 ...
  • 用JAVA写一款自己的小游戏

    万次阅读 多人点赞 2019-02-18 22:30:14
    用JAVA写一款自己的小游戏 我目前也处于个学习的阶段,所以代码会有很多的错误,但是经过我几天的瞎调试目前还是可以玩的,但是可玩性还是很差 说说怎么玩这个游戏把 设计初衷:KoalaChess,顾名思义,我叫他...
  • 我刚学Python,用已掌握的知识已经用"autopy"的功能个鼠标自动点击排队的脚本,但是我想让这个脚本不用在窗口最前端显示也能运行,就是最小化了也能继续在后台继续工作,可是不了解Python的强大功能,下面是...
  • 用JavaScript写一个猜拳小游戏

    千次阅读 2018-07-24 21:13:40
    <tr align="center" height="100px"> <p><font color="coral" size="7"><b id="j">Are you ready?</b></font></p></td> 你选择了:</p><br/> ;color: yellow;"><b>...
  • 用turtle写一个猫和老鼠的小游戏,要求通过鼠标控制老鼠的移动,逃出电脑控制的猫的追捕
  • 用html简单个小游戏

    千次阅读 2020-04-29 19:48:59
    -webkit-transform-origin:100% 100%; -o-transform-origin:100% 100%; } </style> </head> <body> <script type="text/javascript" src="jquery-3.4.1.js"></script> 点我变长"> 您的分数为:<span id="num">0...
  • 用Java写一款小游戏

    千次阅读 2020-08-08 14:18:56
    关于本次程序用到的的技能有:数组、监听器、适配器、定时器、本次用到的Java的swing不需要记住这已经被淘汰 效果展示 窗口 import javax.swing.*; import java.awt.*;... //给窗体设置个标题:
  • 篇《是男人就下100层【第五层】——换肤版2048游戏》中阳光小强对2048游戏用自己的方式进行了实现,并分享了核心源码,这篇阳光小强打算将该项目的所有源代码公开并结合这个实例在这篇文章中介绍一下如何添加...
  • 我们前面讲了几篇关于类的知识点,为了让大家更好的掌握类的概念,并灵活的运用这些知识,我个有趣又好玩的弹球的游戏,一来可以把类的知识融会一下,二来加深对Python的兴趣.你会发现哎呀Python游戏还是蛮...
  • java实现的简单猜数字游戏代码,通过随机数与逻辑判断来实现游戏功能 代码如下: import java.util.InputMismatchException; import java.util.Scanner; public class Main { public static void main...
  • 用c++写一个简单的打字游戏

    千次阅读 2017-11-22 20:57:48
    settextcolor(RGB(rand() % 156 + 100, rand() % 156 + 100, rand() % 256)); for (objy = 0; objy ; objy++) { cleardevice(); outtextxy(objx, objy, obj); Sleep(10); if (_kbhit()) { ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 143,656
精华内容 57,462
关键字:

从一写到100的游戏