侯体宗的博客
  • 首页
  • Hyperf版
  • beego仿版
  • 人生(杂谈)
  • 技术
  • 关于我
  • 更多分类
    • 文件下载
    • 文字修仙
    • 中国象棋ai
    • 群聊
    • 九宫格抽奖
    • 拼图
    • 消消乐
    • 相册

python儿童学游戏编程知识点总结

Python  /  管理员 发布于 7年前   151

python爬虫基本告一段落,琢磨搞点其他的,正好在网上看到一个帖子,一个外国13岁小朋友用python写的下棋程序,内容详细,也有意思,拿来练手。

13岁啊。。 我这年纪还在敲 dir啥的吧

想到原先玩跑跑卡丁车时看到欧酷有个4岁熊孩子玩的完美漂移录像,深受打击,从此退出车坛。。。

废话不多说,记录一下这几天的游戏编程折腾史

游戏规则:6*6的方格棋盘,两个人轮流点击棋盘画横线或竖线,谁成功围成一个格子,这个格子算作此人的积分。

游戏架构:客户端和服务端。

先来看下游戏准备工作,需要用到pygame这个python包。

下载小朋友准备的Resource文件,游戏用到的图片、声音啥的。

一下为BoxGame(客户端)和Server代码,已添加注释。

boxes.py

1 import pygame

import mathfrom PodSixNet.Connection import ConnectionListener,connectionfrom time import sleep# 客户端游戏类class BoxesGame(ConnectionListener):  def initSound(self):    pygame.mixer.music.load("music.wav")    self.winSound=pygame.mixer.Sound('win.wav')    self.loseSound=pygame.mixer.Sound('lose.wav')    self.placeSound=pygame.mixer.Sound('place.wav')    pygame.mixer.music.play()  # 收到来自Server的 action:close指令后调用下面方法  def Network_close(self,data):    exit()  def Network_yourturn(self,data):    self.turn=data['torf']  def Network_startgame(self,data):    self.running=True    self.num=data["player"]    self.gameid=data["gameid"]  def Network_place(self,data):    self.placeSound.play()    x=data["x"]    y=data["y"]    hv=data["is_horizontal"]    if hv:      self.boardh[y][x]=True    else:      self.boardv[y][x]=True  # 设定某个格子为自己的  def Network_win(self,data):    self.owner[data["x"]][data["y"]]="win"    self.boardh[data["y"]][data["x"]]=True    self.boardv[data["y"]][data["x"]]=True    self.boardh[data["y"]+1][data["x"]]=True    self.boardv[data["y"]][data["x"]+1]=True    self.winSound.play()    self.me+=1  def Network_lose(self,data):    self.owner[data["x"]][data["y"]]="lose"    self.boardh[data["y"]][data["x"]]=True    self.boardv[data["y"]][data["x"]]=True    self.boardh[data["y"]+1][data["x"]]=True    self.boardv[data["y"]][data["x"]+1]=True    self.loseSound.play()    self.otherplayer+=1  def __init__(self):    self.justplaced=10    pygame.init()    pygame.font.init()    width, height = 389, 489    self.me = 0    self.otherplayer = 0    self.didwin = False    self.gameid=None    self.num=None    self.num=0    self.screen = pygame.display.set_mode((width, height))    self.owner=[[0 for x in range(6)] for y in range(6)]    self.clock = pygame.time.Clock()    self.turn = True    self.running=False    self.boardh = [[False for x in range(6)] for y in range(7)]    self.boardv = [[False for x in range(7)] for y in range(6)]    print(self.boardh)    print(self.boardv)    self.initGraphics()    self.initSound()    self.drawHUD()    pygame.display.set_caption("Boxes")    # address=raw_input("Host:Port(localhost:8080):")    # try:    #   if not address:    #     host,port="localhost",3721    #   else:    #     host,port=address.split(":")    #   self.Connect((host,port))    # except:    #   print("Error Connecting to Server")    #   print("Usage: host:port")    #   print("eg 127.0.0.1;3721")    #   exit()    self.Connect()    print("Boxes client started")    while not self.running:      self.Pump()      connection.Pump()      self.running=True      sleep(0.01)      print("not running ,connecting...")    if self.num==0:      # self.turn=True      self.marker=self.greenplayer      self.othermarker=self.blueplayer    else:      self.turn=False      self.marker=self.blueplayer      self.othermarker=self.greenplayer  def initGraphics(self):    self.normallinev = pygame.image.load("normalline.png")    self.normallineh = pygame.transform.rotate(self.normallinev, -90)    self.bar_donev = pygame.image.load("bar_done.png")    self.bar_doneh = pygame.transform.rotate(self.bar_donev, -90)    self.hoverlinev = pygame.image.load("hoverline.png")    self.hoverlineh = pygame.transform.rotate(self.hoverlinev, -90)    # self.boardh[5][4]=True    # self.boardv[5][5]=True    self.separators = pygame.image.load("separators.png")    self.score_panel = pygame.image.load("score_panel.png")    self.redindicator = pygame.image.load("redindicator.png")    self.greenindicator = pygame.image.load("greenindicator.png")    self.greenplayer = pygame.image.load("greenplayer.png")    self.blueplayer = pygame.image.load("blueplayer.png")    self.winningscreen = pygame.image.load("youwin.png")    self.gameover = pygame.image.load("gameover.png")  def drawBoard(self):    for x in range(6):      for y in range(7):        if not self.boardh[y][x]:          self.screen.blit(self.normallineh, [(x) * 64 + 5, (y) * 64])        else:          self.screen.blit(self.bar_doneh, [(x) * 64 + 5, (y) * 64])    for x in range(7):      for y in range(6):        if not self.boardv[y][x]:          self.screen.blit(self.normallinev, [(x) * 64, (y) * 64 + 5])        else:          self.screen.blit(self.bar_donev, [(x) * 64, (y) * 64 + 5])  def update(self):    # 判断方格是否已经都有归属    if self.me+self.otherplayer==36:      self.didwin=True if self.me>self.otherplayer else False      return 1    self.justplaced-=1    # print('pump connect info')    connection.Pump()    self.Pump()    # print('pump connect info finish')    self.clock.tick(60)    self.screen.fill(0)    self.drawBoard()    self.drawHUD()    self.drawOwnermap()    for event in pygame.event.get():      if event.type == pygame.QUIT:        exit()    mouse = pygame.mouse.get_pos()    xpos = int(math.ceil((mouse[0] - 32) / 64.0))    ypos = int(math.ceil((mouse[1] - 32) / 64.0))    # 判断鼠标位置更接近与那条线    is_horizontal = abs(mouse[1] - ypos * 64) < abs(mouse[0] - xpos * 64)    ypos = ypos - 1 if mouse[1] - ypos * 64 < 0 and not is_horizontal else ypos    xpos = xpos - 1 if mouse[0] - ypos * 64 < 0 and is_horizontal else xpos    board = self.boardh if is_horizontal else self.boardv    isoutofbounds = False    try:      if not board[ypos][xpos]: self.screen.blit(self.hoverlineh if is_horizontal else self.hoverlinev,    [xpos * 64 + 5 if is_horizontal else xpos * 64,    ypos * 64 if is_horizontal else ypos * 64 + 5])    except:      isoutofbounds = True      pass    if not isoutofbounds:      alreadyplaced = board[ypos][xpos]    else:      alreadyplaced = False    # 鼠标点击时,发送place信号给自己划线    if pygame.mouse.get_pressed()[0] and not alreadyplaced and not isoutofbounds and self.turn==True and self.justplaced<=10:      self.justplaced=10      if is_horizontal:        self.boardh[ypos][xpos] = True        self.Send({"action":"place","x":xpos,"y":ypos,"is_horizontal":is_horizontal,"gameid":self.gameid,"num":self.num})      else:        self.boardv[ypos][xpos] = True        self.Send({"action":"place","x":xpos,"y":ypos,"is_horizontal":is_horizontal,"gameid":self.gameid,"num":self.num})    pygame.display.flip()  # 画记分区域  def drawHUD(self):    self.screen.blit(self.score_panel, [0, 389])    myfont = pygame.font.SysFont(None, 32)    label = myfont.render("Your turn", 1, (255, 255, 255))    self.screen.blit(label, (10, 400))    self.screen.blit(self.greenindicator if self.turn else self.redindicator ,(130, 395))    myfont64 = pygame.font.SysFont(None, 64)    myfont20 = pygame.font.SysFont(None, 20)    scoreme = myfont64.render(str(self.me), 1, (255, 255, 255))    scoreother = myfont64.render(str(self.otherplayer), 1, (255, 255, 255))    scoretextme = myfont20.render("You", 1, (255, 255, 255))    scoretextother = myfont20.render("Other Player", 1, (255, 255, 255))    self.screen.blit(scoretextme, (10, 425))    self.screen.blit(scoreme, (10, 435))    self.screen.blit(scoretextother, (280, 425))    self.screen.blit(scoreother, (280, 435))  # 给占领与被占领格子着色  def drawOwnermap(self):         for x in range(6):      for y in range(6):        if self.owner[x][y]!=0:          if self.owner[x][y]=="win":self.screen.blit(self.marker,(x*64+5,y*64+5))          if self.owner[x][y]=="lose":self.screen.blit(self.othermarker,(x*64+5,y*64+5))  # 游戏结束后显示gameover或winning的图案  def finished(self):    self.screen.blit(self.gameover if not self.didwin else self.winningscreen,(0,0))    while 1:      for event in pygame.event.get():        if event.type==pygame.QUIT:          exit()      pygame.display.flip()bg = BoxesGame()while 1:  if bg.update()==1:    breakbg.finished()

server.py

1 __author__ = 'Administrator'

import PodSixNet.Channelimport PodSixNet.Serverfrom time import sleep# 定义客户端通道,继承PodSixNet.Channel.Channelclass ClientChannel(PodSixNet.Channel.Channel):  def Network(self,data):    print data  def Network_place(self,data):    hv=data["is_horizontal"]    x=data["x"]    y=data["y"]    # 客户标号    num=data["num"]    # 本游戏id    self.gameid=data["gameid"]    self._server.placeLine(hv,x,y,data,self.gameid,num)  def Close(self):    self._server.close(self.gameid)# 定义游戏服务端class BoxesServer (PodSixNet.Server.Server):  channelClass = ClientChannel  def __init__(self,*args,**kwargs):    PodSixNet.Server.Server.__init__(self,*args,**kwargs)    self.games=[]    self.queue=None    self.currentIndex=0  def Connected(self,channel,addr):    print 'new connection:',channel    # 如果队列为空,则新建一局game    if self.queue==None:      self.currentIndex+=1      channel.gameid=self.currentIndex      self.queue=Game(channel,self.currentIndex)    #如果队列中已有一局game在等待,则将新连进来的channel作为第二名游戏者与等待游戏者配对,加入games[]列表,将queue清空    else:      channel.gameid=self.currentIndex      self.queue.player1=channel      self.queue.player0.Send({"action":"startgame","player":0,"gameid":self.queue.gameid})      self.queue.player1.Send({"action":"startgame","player":1,"gameid":self.queue.gameid})      self.games.append(self.queue)      self.queue=None  # def placeLine(self,is_h,x,y,data,gameid,num):  #   if num==self.turn:  #     self.turn=0 if self.turn else 1  #     self.player1.Send({"action":"yourturn","torf":True if self.turn==1 else False})  #     self.player0.Send({"action":"yourturn","torf":True if self.turn==0 else False})  #     if is_h:  #       self.boardh[y][x]=True  #     else:  #       self.boardv[y][x]=True  #     self.player0.Send(data)  #     self.player1.Send(data)  #通知GameServer哪句游戏要划线,调用游戏placeLine  def placeLine(self,is_h,x,y,data,gameid,num):    game=[a for a in self.games if gameid==a.gameid]    if len(game)==1:      game[0].placeLine(is_h,x,y,data,num)  # 关闭某局game  def close(self,gameid):    try:      game=[a for a in self.games if a.gameid==gameid][0]      game.player0.Send({"action":"close"})      game.player1.Send({"action":"close"})    except:      pass  # 判断方格归属  def tick(self):    index=0    # 状态未改变 code 3    change=3    # 扫描每局游戏    for game in self.games:      change=3      # 扫描2次,因为存在放置一个线条完成两个方格占领的情况      for time in range(2):        for y in range(6):          for x in range(6):# 判断是否是新围成的方格if game.boardh[y][x] and game.boardv[y][x] and game.boardh[y+1][x] and game.boardv[y][x+1] and not game.owner[x][y]:  # 是否为己方围成的,围成的一方可以继续走一步  # 此处self.games[index]能否替换为game?  if self.games[index].turn==0:    self.games[index].owner[x][y]=2    game.player1.Send({"action":"win","x":x,"y":y})    game.player0.Send({"action":"lose","x":x,"y":y})    change=1    print("player1 win 1 grid")  else:    self.games[index].owner[x][y]=1    game.player0.Send({"action":"win","x":x,"y":y})    game.player1.Send({"action":"lose","x":x,"y":y})    change=0    print("player0 win 1 grid")      # 如果状态改变了(即有一方完成了方格占领)则下一步仍由该方走棋;否则正常交替走棋      self.games[index].turn=change if change!=3 else self.games[index].turn      game.player1.Send({"action":"yourturn","torf":True if self.games[index].turn==1 else False})      game.player0.Send({"action":"yourturn","torf":True if self.games[index].turn==0 else False})      index+=1    self.Pump()# 单纯一局游戏的控制类class Game:  def __init__(self,player0,currentIndex):    self.turn=0    self.owner=[[False for x in range(6)] for y in range(6)]    self.boardh=[[False for x in range(6)] for y in range(7)]    self.boardv=[[False for x in range(7)] for y in range(6)]    self.player0=player0    self.player1=None    self.gameid=currentIndex    # while not self.running:    #   self.Pump()    #   connection.Pump()    #   sleep(0.01)    # if self.num==0:    #   self.turn=True    #   self.marker=self.greenplayer    #   self.othermarker=self.blueplayer    # else:    #   self.turn=False    #   self.marker=self.blueplayer    #   self.othermarker=self.greenplayer  # 划线  def placeLine(self,is_h,x,y,data,num):    if num==self.turn:      self.turn=0 if self.turn else 1      self.player1.Send({"action":"yourturn","torf":True if self.turn==1 else False})      self.player0.Send({"action":"yourturn","torf":True if self.turn==0 else False})      if is_h:        self.boardh[y][x]=True      else:        self.boardv[y][x]=True      self.player0.Send(data)      self.player1.Send(data)  # def Network_palce(self,data):  #   x=data["x"]  #   y=data["y"]  #   hv=data["is_horizontal"]  #   if hv:  #     self.boardh[y][x]=True  #   else:  #     self.boardv[y][x]=Trueprint "Staring server on localhost"address=raw_input("Host:Port(localhost:8080):")if not address:  host,port="localhost",31425  print("default host and port")  print(host,":",port)else:  host,port=address.split(":")  print(host,":",port)boxesServer=BoxesServer( localaddr=("127.0.0.1", 31425))# boxesServer=BoxesServer()while True:  boxesServer.Pump()  boxesServer.tick()  sleep(0.01) 就是这样,休息,休息一下。

以上就是本次介绍的儿童学习python游戏编程的全部知识点内容,感谢大家的支持。


  • 上一条:
    Python3日期与时间戳转换的几种方法详解
    下一条:
    详解Python3之数据指纹MD5校验与对比
  • 昵称:

    邮箱:

    0条评论 (评论内容有缓存机制,请悉知!)
    最新最热
    • 分类目录
    • 人生(杂谈)
    • 技术
    • linux
    • Java
    • php
    • 框架(架构)
    • 前端
    • ThinkPHP
    • 数据库
    • 微信(小程序)
    • Laravel
    • Redis
    • Docker
    • Go
    • swoole
    • Windows
    • Python
    • 苹果(mac/ios)
    • 相关文章
    • 在python语言中Flask框架的学习及简单功能示例(0个评论)
    • 在Python语言中实现GUI全屏倒计时代码示例(0个评论)
    • Python + zipfile库实现zip文件解压自动化脚本示例(0个评论)
    • python爬虫BeautifulSoup快速抓取网站图片(1个评论)
    • vscode 配置 python3开发环境的方法(0个评论)
    • 近期文章
    • 在go语言中使用api.geonames.org接口实现根据国际邮政编码获取地址信息功能(1个评论)
    • 在go语言中使用github.com/signintech/gopdf实现生成pdf分页文件功能(0个评论)
    • gmail发邮件报错:534 5.7.9 Application-specific password required...解决方案(0个评论)
    • 欧盟关于强迫劳动的规定的官方举报渠道及官方举报网站(0个评论)
    • 在go语言中使用github.com/signintech/gopdf实现生成pdf文件功能(0个评论)
    • Laravel从Accel获得5700万美元A轮融资(0个评论)
    • 在go + gin中gorm实现指定搜索/区间搜索分页列表功能接口实例(0个评论)
    • 在go语言中实现IP/CIDR的ip和netmask互转及IP段形式互转及ip是否存在IP/CIDR(0个评论)
    • PHP 8.4 Alpha 1现已发布!(0个评论)
    • Laravel 11.15版本发布 - Eloquent Builder中添加的泛型(0个评论)
    • 近期评论
    • 122 在

      学历:一种延缓就业设计,生活需求下的权衡之选中评论 工作几年后,报名考研了,到现在还没认真学习备考,迷茫中。作为一名北漂互联网打工人..
    • 123 在

      Clash for Windows作者删库跑路了,github已404中评论 按理说只要你在国内,所有的流量进出都在监控范围内,不管你怎么隐藏也没用,想搞你分..
    • 原梓番博客 在

      在Laravel框架中使用模型Model分表最简单的方法中评论 好久好久都没看友情链接申请了,今天刚看,已经添加。..
    • 博主 在

      佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 @1111老铁这个不行了,可以看看近期评论的其他文章..
    • 1111 在

      佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 网站不能打开,博主百忙中能否发个APP下载链接,佛跳墙或极光..
    • 2016-10
    • 2016-11
    • 2018-04
    • 2020-03
    • 2020-04
    • 2020-05
    • 2020-06
    • 2022-01
    • 2023-07
    • 2023-10
    Top

    Copyright·© 2019 侯体宗版权所有· 粤ICP备20027696号 PHP交流群

    侯体宗的博客