学习python编程,在新东方少儿编程官网的自由创作平台做的一些作品。
可以在线运行,效果如下(在新页面中打开链接):
代码如下(用到平台自定义的xdf库):
from xdf import *
keys = {}
def keydown(key, keyCode):
keys[str(key)] = True
#print(key, 'down')
def keyup(key, keyCode):
key = str(key)
if key in keys:
keys[key] = False
#print(key, 'up')
def isDown(key):
return (key in keys) and keys[key]
class Sprite:
def __init__(self, dis):
self.id = 0
self.x = 0
self.y = 0
self.w = 1
self.h = 1
self.visible = True
self.dis = dis
def front(self):
self.dis.front()
def move(self, x, y):
self.x = x
self.y = y
def change(self, value):
self.dis.change(value)
def update(self, pVisible):
self.dis.move(self.x, self.y)
if pVisible and self.visible:
self.dis.show()
else:
self.dis.hide()
class SpriteSheet(Sprite):
def __init__(self, arr, config):
self.isPlaying = True
self.isFlag = False
self.currentFrame = 0
self.totalFrames = len(arr)
self.stamps = []
self.config = config
self.flipped = False
self.flipArr = []
for i in range(len(arr)):
sp = stamp(arr[i])
self.stamps.append(sp)
sp.hide()
self.flipArr.append(False)
Sprite.__init__(self, self.stamps[0])
def play(self):
self.isPlaying = True
def stop(self):
self.isPlaying = False
def gotoAndStop(self, n):
self.currentFrame = n;
self.stop()
def gotoAndPlay(self, n):
self.currentFrame = n;
self.play()
def nextFrame(self):
self.currentFrame = self.currentFrame + 1
if self.isFlag:
if self.currentFrame > self.flagEnd:
self.currentFrame = self.flagStart
elif self.currentFrame >= self.totalFrames:
self.currentFrame = 0
def playFlag(self, flag):
if flag in self.config:
a = self.config[flag]
self.flagStart = a[0]
self.flagEnd = a[1]
self.isFlag = True
self.gotoAndPlay(self.flagStart);
def clearPlayFlag(self):
self.isFlag = False
def update(self, pVisible = True):
if self.isPlaying:
self.nextFrame()
for i in range(len(self.stamps)):
self.stamps[i].hide()
self.dis = self.stamps[self.currentFrame]
if self.flipped != self.flipArr[self.currentFrame]:
self.flipArr[self.currentFrame] = self.flipped
self.dis.flip()
super().update(pVisible)
class Container:
def __init__(self):
self.children = []
self.visible = True
def show(self):
self.visible = True
def hide(self):
self.visible = False
def update(self, pVisible = True):
for i in range(len(self.children)):
self.children[i].update(pVisible and self.visible)
class HMenuLayer(Container):
def __init__(self):
Container.__init__(self)
self.bg = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782826_265032.jpg'))
self.gamename = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782791_842716.png'))
self.shuoming = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782905_431833.png'))
self.btn = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686021917093_359914.png'))
self.bg.move(384, 512)
self.gamename.move(184, 312)
self.shuoming.move(380, 700)
self.btn.move(380, 860)
self.btn.dis.tap = self.onStart
self.children = [self.bg, self.gamename, self.shuoming, self.btn]
def onStart(self):
gameStart()
class HOverlayer(Container):
def __init__(self):
Container.__init__(self)
self.bg = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686023293202_314981.png'))
self.scoreBg = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782909_737697.png'))
self.tfCj = Sprite(text('成绩', 384, 420, 20, '#00FF66', 'center'))
self.tfFloor = Sprite(text('00', 384, 500, 30, '#FF9900', 'center'))
self.tfScore = Sprite(text('00', 384, 540, 30, '#FF6666', 'center'))
self.btn = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686028239057_123081.png'))
self.bg.move(384, 512)
self.scoreBg.move(384, 512)
self.tfCj.move(384, 420)
self.tfFloor.move(384, 500)
self.tfScore.move(384, 540)
self.btn.move(384, 595)
self.btn.dis.tap = self.onRestart
self.children = [self.bg, self.scoreBg, self.tfCj, self.tfFloor, self.tfScore, self.btn]
self.setScore(0,0)
def setScore(self, floor, score):
self.tfFloor.change('层数:' + str(floor))
self.tfScore.change('分数:' + str(score))
def onRestart(self):
gameRestart()
class HLadderLayer(Container):
def __init__(self):
Container.__init__(self)
self.pool = []
self.reset()
self.id = 1
def update(self, pVisible = True):
super().update(pVisible)
for i in range(len(self.pool)):
self.pool[i].visible = False
self.pool[i].update(pVisible)
def setYoffset(self, value):
for i in range(len(self.children)):
lad = self.children[i]
lad.y += value
while self.children[0].y > 1024 + 25:
lad = self.children.pop(0)
self.pool.append(lad)
while self.children[-1].y > 0:
self.addLadder(self.children[-1].y - 100)
def reset(self):
self.id = 1
while len(self.children):
self.pool.append(self.children.pop())
for i in range(9):
self.addLadder(1024 - 200 -i*100)
def getLadders(self):
return self.children
def createLadder(self):
if len(self.pool):
return self.pool.pop()
lad = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782879_239311.png'))
lad.w = 220
lad.h = 20
return lad
def addLadder(self, y):
lad = self.createLadder()
lad.x = random(80, 688)
lad.y = y
lad.visible = True
self.children.append(lad)
lad.id = self.id
self.id += 1
class HBgLayer(Container):
def __init__(self):
Container.__init__(self)
self.bg = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017783064_242131.jpg'))
self.ground = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782879_375451.png'))
self.bg.x = 384
self.ground.x = 384
self.ground.w = 480
self.ground.h = 24
self.qiangArr = []
self.children = [self.bg, self.ground]
for i in range(3):
qiangR = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686032051227_921808.png'))
qiangL = Sprite(stamp('https://code-file.xdf.cn/files/dingdangweb/20230606/1686032051231_983939.png'))
self.qiangArr.append(qiangL)
self.qiangArr.append(qiangR)
qiangL.x = 80
qiangR.x = 688
self.children.append(qiangL)
self.children.append(qiangR)
self.reset()
def update(self, pVisible = True):
super().update(pVisible)
for i in range(len(self.qiangArr)):
self.qiangArr[i].front()
def reset(self):
self.bg.y = -176
self.ground.visible = True
self.ground.y = 1012
for i in range(3):
qiangL = self.qiangArr[i * 2]
qiangR = self.qiangArr[i * 2 + 1]
qiangL.y = 744 - 560*i
qiangR.y = 744 - 560*i
def setYoffset(self, value):
for i in range(3):
qy = self.qiangArr[2*i].y
if qy > 744:
qy -= 560 * 3
self.qiangArr[2*i].y = self.qiangArr[2*i + 1].y = qy
if self.ground.visible:
self.ground.y += value
if self.ground.y > 1024+200+25:
self.ground.visible = False
self.bg.y += value * 0.2
if self.bg.y > 1200:
self.bg.y -= 800
def getGround(self):
return self.ground
class Hero(Container):
def __init__(self):
Container.__init__(self)
self.w = 40 #156
self.h = 100 #112
self.sp = SpriteSheet(
[
'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782884_441334.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782789_777162.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782868_528853.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782879_421421.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782894_144746.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782864_319894.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782867_785734.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782864_084225.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782894_974575.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782845_061008.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782804_792339.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782871_063850.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782827_010127.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782783_055114.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782783_165885.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782845_347436.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782845_099353.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782866_974514.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782789_491249.png'
,'https://code-file.xdf.cn/files/dingdangweb/20230606/1686017782864_583559.png'
],
{
'stand': [0, 4],
'run': [5, 10],
'jump': [11, 13],
'jump2': [14, 19]
}
)
self.x = 0
self.y = 0
self.speedX = 0
self.speedY = 0
self.inSpace = False
self.state = ""
self.MAX_SPEED = 20
self.AX = 2
self.FY = -25
self.children = [self.sp]
self.reset()
def update(self, pVisible=True):
self.sp.x = self.x
self.sp.y = self.y
super().update(pVisible)
def setScale(self, sc):
if sc < 0:
self.sp.flipped = True
else:
self.sp.flipped = False
def runLeft(self):
if not self.inSpace:
self.run()
self.setScale(-1)
self.speedX -= self.AX
if self.speedX < -self.MAX_SPEED:
self.speedX = -self.MAX_SPEED
def runRight(self):
if not self.inSpace:
self.run()
self.setScale(1)
self.speedX += self.AX
if self.speedX > self.MAX_SPEED:
self.speedX = self.MAX_SPEED
def jumpUp(self):
if not self.inSpace:
self.speedY = self.FY - abs(self.speedX / self.MAX_SPEED)*35
if self.speedY < -40:
self.jump2()
else:
self.jump()
def jump(self):
if self.changeState('jump'):
self.inSpace = True
def jump2(self):
if self.changeState('jump2'):
self.inSpace = True
def run(self):
self.changeState('run')
def stand(self):
self.changeState('stand')
def changeState(self, state):
if self.state != state:
self.sp.playFlag(state)
self.state = state
return True
return False
def reset(self):
self.speedX = 0
self.speedY = 0
self.inSpace = False
self.stand()
self.x = 384
self.y = 1024-56
def hitTest(self, sp):
rect0 = Rect(self.x, self.y, self.w, self.h)
rect1 = Rect(sp.x, sp.y, sp.w, sp.h)
flag = not (rect1.left > rect0.right
or rect1.right < rect0.left
or rect1.top > rect0.bottom
or rect1.bottom < rect0.top
) and self.speedY > 0 and self.y < sp.y
if flag:
self.y = sp.y - sp.h / 2 - self.h / 2
self.speedY = 0
return flag
class Rect:
def __init__(self, x, y, w, h):
self.x = x
self.y = y
self.w = w
self.h = h
self.left = x - w / 2
self.top = y - h / 2
self.right = x + w / 2
self.bottom = y + h /2
class FlyText(Sprite):
def __init__(self, tf):
Sprite.__init__(self, tf)
self.life = 0
self.step = 0
def flyText(self, text, life, x, y, dy):
self.change(text)
self.life = life
self.x = x
self.y = y
self.step = dy / life
def update(self, pVisible):
self.life = max(0, self.life-1)
self.visible = self.life > 0
if self.life > 0:
self.y += self.step
super().update(pVisible)
self.front()
class HGameLayer(Container):
def __init__(self):
Container.__init__(self)
self.autoMove = False
self.score = 0
self.floor = 0
self.isRunning = False
self.bgLayer = HBgLayer()
self.ladderLayer = HLadderLayer()
self.hero = Hero()
self.tfFloor = Sprite(text('00', 0, 0, 40, '#FF6600'))
self.tfScore = Sprite(text('00', 0, 0, 40, '#FF6600'))
self.tfFloor.move(10, 50)
self.tfScore.move(10, 100)
self.flyTf = FlyText(text('00', 0, 0, 50, '#FF0000'))
self.ladderLayer.setYoffset(0)
self.children = [self.bgLayer, self.ladderLayer, self.hero, self.tfFloor, self.tfScore, self.flyTf]
def setScore(self, floor, score):
self.tfFloor.change('层数:' + str(floor))
self.tfScore.change('分数:' + str(score))
def update(self, pVisible = True):
super().update(pVisible)
self.tfFloor.front()
self.tfScore.front()
self.setScore(self.floor, self.score)
#print('is run', self.isRunning)
if not self.isRunning:
return
hero = self.hero
if isDown('39') or yaogan.isRight():
hero.runRight()
elif isDown('37') or yaogan.isLeft():
hero.runLeft()
if isDown('38') or isDown('32') or yaogan.isSpace():
hero.jumpUp()
hero.x += hero.speedX
hero.speedX *= 0.90
if hero.x > 558:
hero.x = 558
hero.speedX *= 0.5
elif hero.x < 210:
hero.x = 210
hero.speedX *= 0.5
if abs(hero.speedX) < 0.5:
hero.speedX = 0
hero.speedY += 2
hero.y += hero.speedY
hero.inSpace = True
fallFlag = hero.speedY > 2
if hero.speedY > 0:
# 检测地板
# print('hit test floor')
ground = self.bgLayer.getGround()
if hero.hitTest(ground):
hero.inSpace = False
if fallFlag:
pass
else:
# 检测梯子
ladders = self.ladderLayer.getLadders()
for i in range(len(ladders)):
ladder = ladders[i]
# print('hit test ladder')
if hero.hitTest(ladder):
hero.inSpace = False
if fallFlag:
pass
ind = ladder.id
if self.floor < ind:
step = ind - self.floor
if step > 3:
self.score += 10
self.flyTf.flyText('连跳' + str(step) + '层', 40, hero.x, hero.y, -300)
self.floor = ind
self.score += step * 10
if hero.y < 512:
self.autoMove = True
if self.autoMove:
self.bgLayer.setYoffset(2)
self.ladderLayer.setYoffset(2)
if hero.y < 400:
step = min(40, 400 - hero.y)
hero.y += step
self.bgLayer.setYoffset(step)
self.ladderLayer.setYoffset(step)
if not hero.inSpace:
if hero.speedX:
hero.run()
else:
hero.stand()
if self.autoMove and hero.y > 1024:
self.stop()
self.gameOver()
def gameOver(self):
gameOver()
def reset(self):
self.bgLayer.reset()
self.ladderLayer.reset()
self.hero.reset()
self.autoMove = False
self.floor = 0
self.score = 0
def start(self):
self.reset()
self.isRunning = True
def stop(self):
self.isRunning = False
gameLayer = HGameLayer()
menuLayer = HMenuLayer()
overLayer = HOverlayer()
gameLayer.visible = False
overLayer.visible = False
def hideAll():
gameLayer.visible = False
overLayer.visible = False
menuLayer.visible = False
def gameRestart():
hideAll()
menuLayer.visible = True
yaogan.show()
def gameStart():
hideAll()
gameLayer.visible = True
gameLayer.start()
yaogan.show()
def gameOver():
hideAll()
overLayer.visible = True
overLayer.setScore(gameLayer.floor, gameLayer.score)
yaogan.hide()
def loop():
menuLayer.update()
overLayer.update()
gameLayer.update()
yaogan.front()
from xdf import *
class Yaogan:
def __init__(self):
y0 = 1024-100
x0 = 100
x1 = 768-100
self.x0 = x0
self.y0 = y0
self.x1 = x1
self.c1 = circle(x0, y0, 100, 'transparent', 'blue')
self.c2 = circle(x0, y0, 30, 'red')
self.c3 = circle(x1, y0, 100, 'rgb(255, 0, 0, 0.5)')
self.isDown1 = False
self.isDown3 = False
self.dp = [0, 0]
self.visible = True
def hide(self):
self.c1.move(0, 1300)
self.c2.move(0, 1300)
self.c3.move(0, 1300)
def show(self):
self.c1.move(self.x0, self.y0)
self.c2.move(self.x0, self.y0)
self.c3.move(self.x1, self.y0)
def front(self):
self.c1.front()
self.c2.front()
self.c3.front()
def isLeft(self):
return self.dp[0] < -10
def isRight(self):
return self.dp[0] > 10
def isSpace(self):
return self.isDown3
def touch(self, x, y):
if self.c1.hits(x, y):
self.isDown1 = True
elif self.c3.hits(x, y):
self.isDown3 = True
def touching(self, x, y):
if self.c1.hits(x, y):
self.c2.move(x, y)
self.dp = [x - self.x0, y - self.y0]
def untouch(self, x, y):
if self.c1.hits(x, y) or x <= 768 / 2:
self.isDown1 = False
self.c2.move(self.x0, self.y0)
self.dp = [0, 0]
elif self.c3.hits(x, y) or x > 768 / 2:
self.isDown3 = False
yaogan = Yaogan()
yaogan.hide()
def touch():
yaogan.touch(x, y)
def untouch():
yaogan.untouch(x, y)
def touching():
yaogan.touching(x, y)
也可以下载代码,本地python环境运行(用pygame封装了xdf库)。
发表评论:
◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。