python网络编程游戏
学过一点计算机网络编程的都知道,TCP/IP协议,然后我就想,我们学习的局域网游戏是怎么做的呢,经过我煞费苦心的一番研究,终于走出了这条门槛,网络编程,即socket套接字作为接口,一般通过ip地址和端口映射作为网络的门牌号,来找到对方机器在网络中的具体位置。
我们配合pygame来实现一个局域网遥控的程序。
首先我们先上游戏运行截图:
下图是服务器打开时候的等待客户机链接的状态,我设置的端口是50007端口。
当客户机链接服务器成功后就如下图,左边是服务器控制的状态界面,右边是客户机被服务器控制的状态界面,从右图可以看出,客户机的飞机被服务器控制然后会实现相应的移动。
接下啦我们看看这样一个c/s模式怎么搭建.
服务器端基本程序如下:
from socket import *
HOST = ''
PORT = 21567
BUFSIZ = 1024
ADDR = (HOST,PORT)
tcpSerSock = socket(AF_INET, SOCK_STREAM)
tcpSerSock.bind(ADDR)
tcpSerSock.listen(5)
while True:
print 'waiting for connection...'
tcpCliSock,addr = tcpSerSock.accept()
print '...connected from: ',addr
while True:
data = tcpCliSock.recv(BUFSIZ)
if not data:
break
print "="*20
print "[From Client]:",data
message = raw_input("Service>")
tcpCliSock.send(message)
tcpSerSock.close()
客户端基本程序如下:
from socket import *
HOST = '192.168.43.252'
PORT = 21567
BUFSIZ = 1024
ADDR = (HOST,PORT)
tcpCliSock = socket(AF_INET,SOCK_STREAM)
tcpCliSock.connect(ADDR)
while True:
data = raw_input("Client>")
if not data:
break
tcpCliSock.send(data)
message = tcpCliSock.recv(BUFSIZ)
if not data:
break
print "="*20
print "[From Servier]:",message
tcpCliSock.close()
有了上面这些基本的c/s架构程序我们就可以在上面填写游戏完全的代码了。
首先服务端:
先初始化所有变量
# -*- coding:utf-8 -*-
# TCP protrocl
import socket
import os
import pygame,sys
from sys import exit
from pygame.locals import *
import codecs
pygame.init()
words ={'how are you?':'Fine ,thank you'}
Itdatas=[]#数据存储
HOST =''
PORT=50007
s =socket.socket(socket.AF_INET,socket.SOCK_STREAM)
#绑定socket
s.bind((HOST,PORT))
#开始监听
s.listen(1)
print ('Listening at port :',PORT)
conn,addr =s.accept()
print ('Connected by',addr)
#-----------------------pygame-------------------
WIDTH = 640
HEIGHT = 480
screen = pygame.display.set_mode([WIDTH,HEIGHT],0,32)
caption = pygame.display.set_caption('GAME')
screen.fill([0,0,0])
name = u"hello"
fly = pygame.image.load('myfly.gif').convert_alpha()
fly_width = fly.get_width()
fly_height = fly.get_height()
fly_x = WIDTH/2-fly_width/2
fly_y = HEIGHT-fly_height
pygame.display.flip()
#-----------------------pygame-------------------
游戏就是一个死循环,然后在里面写入完整控制端的内容。
screen.fill([0,0,0])
myfon = pygame.font.Font(‘poster.ttf’,50)
myfont = myfon.render(name,True,(128,128,128))
name = u'hello'
for event in pygame.event.get():
if event.type == QUIT:
exit()
data = conn.recv(1024)
data=data.decode()
if data == 'exit':
print ('[system exit!!!]')
break
elif data == '0':
name = u"恭喜1!"
screen.blit(myfont,(100,0))
elif data == '1':
name = u"你好2!"
screen.blit(myfont,(100,0))
elif data == '2':
name = u"哈喽3!"
screen.blit(myfont,(100,0))
else:
name = data
screen.blit(myfont,(100,0))
screen.blit(fly,(fly_x,fly_y))
if data == 'w' or data == 'W':
fly_y -= 0.6
name = u'飞机前进'
if data == 's' or data == 'S':
fly_y += 0.6
name = u'飞机后退'
if data == 'a' or data == 'A':
fly_x -= 0.6
name = u'飞机做左移'
if data == 'd' or data == 'D':
fly_x += 0.6
name = u'飞机右移'
if fly_x <= 0 :
fly_x = 0
if fly_x+fly_width >= WIDTH:
fly_x = WIDTH-fly_width
if fly_y <= 0 :
fly_y = 0
if fly_y+fly_height >= HEIGHT:
fly_y = HEIGHT-fly_height
print ('Received message:',data)
conn.sendall(words.get(data,'[Sended]').encode())
#服务器发送模块
#c=raw_input('Input the content you want to send:')
#conn.sendall(c.encode())
#data=data.decode()
#if c.lower()=='bye':
# break
#print 'wating...'
pygame.display.update()
然后是客户端程序:
初始化所有变量
import os
import pygame,sys
from sys import exit
from pygame.locals import *
pygame.init()
try:
files = open('serve.txt','r')
except:
files = open('serve.txt','w')
serve_name = 'localhost'
files.write(serve_name)
service_ip=files.read()
HOST= service_ip#服务端的IP地址
PORT=50007 #服务端的端口号
s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
#-----------------------pygame-------------------
WIDTH = 640
HEIGHT = 480
screen = pygame.display.set_mode([WIDTH,HEIGHT],0,32)
caption = pygame.display.set_caption('GAME')
screen.fill([0,0,0])
wb = pygame.image.load('w.png').convert_alpha()
sb = pygame.image.load('s.png').convert_alpha()
ab = pygame.image.load('a.png').convert_alpha()
db = pygame.image.load('d.png').convert_alpha()
img_w = wb.get_width()
img_h = wb.get_height()
pygame.display.flip()
c='w'
name = u'正在前进'
myfon = pygame.font.Font('poster.ttf',50)
myfont = myfon.render(name,True,(128,128,128))
#-----------------------pygame-------------------
try:
s.connect((HOST,PORT))
except Exception as e:
print ('Server not found or not open')
sys.exit()
我们把最开始客户端默认移动的方向写入文件contro.txt中,wsad代表上下左右四个移动方向,然后在进行读取,我们把服务器端的ip地址配置文件放入serve.txt文本文件中,这样方便我么那以后连接其他服务器时做出相应的ip动态配置改变。可维护性能提高。
然后在死循环中写入客户端动画代码:
screen.fill([0,0,0])
myfon = pygame.font.Font('poster.ttf',50)
myfont = myfon.render(name,True,(128,128,128))
#c=raw_input('Input the content you want to send:')
#file = open('contro.txt','r')
#c=file.read()
#file.close()
for event in pygame.event.get():
if event.type == QUIT:
exit()
if event.type == KEYDOWN:
if event.key == K_w:
c = 'w'
name = u'前进了'
if event.key == K_s:
c = 's'
name = u'后退了'
if event.key == K_a:
c = 'a'
name = u'左移动'
if event.key == K_d:
c = 'd'
name = u'右移动'
screen.blit(myfont,(50,60))
screen.blit(wb,[WIDTH/2-img_w/2,HEIGHT/2-img_w-85])
screen.blit(sb,[WIDTH/2-img_w/2,HEIGHT/2+30])
screen.blit(ab,[WIDTH/2-img_w-70,HEIGHT/2-70])
screen.blit(db,[WIDTH/2+70,HEIGHT/2-70])
s.sendall(c.encode()) #发送数据
data=s.recv(1024) #接收数据
data=data.decode()
if c == 'exit':
print ('[system exit!!!]')
break
#客户端接受模块
#print 'wating...'
#datas=s.recv(1024) #接收数据
#if not datas:
# print 'not data'
#print 'Received message:',datas
pygame.display.update()
然后新鲜的网络游戏框架就搭建好了,是不是很有意思。
最后项目链接在这里
https://download.csdn.net/download/qq_25755645/12238469?spm=1001.2014.3001.5503