#Globale Variabeln initiieren
#Nach Präferenz ändern: w = 0 h = 0 playerY = 3 playerZ = 20 buildGlass = True
#Nicht ändern: board = 0 piece = 0 pieceX = 0 pieceY = 0 color = DIAMOND_BLOCK isRunning = False origin = player.position() score = 0 unusedPieces = range(7)
#Generelle Funktionen
def startTetris():
global w
global h
global playerZ
global board
global piece
global pieceX
global pieceY
global isRunning
global origin
global score
global unusedPieces
#erstellen einer zweidimensionalen Liste zum Speichern der Spielfläche
# (0/1) (1/1)
# (0/0) (1/0)
board = []
for i in range(w):
temparr = range(h)
board[i] = temparr
for j in range(h):
board[i][j] = 0
#erstellen des ersten Tetrominos
unusedPieces = range(7)
pieceX = Math.round(w/2) - 2
pieceY = h - 1
getPiece()
#Spieler zentrieren und Agenten wegteleportieren
agent.teleport_to_player()
player.teleport(agent.get_position())
origin = player.position()
player.execute("tp ~ ~ ~ facing ~ ~ ~1")
agent.teleport(pos(0, -10, 0), SOUTH)
#"Spielkonsole" bauen
makeBoard(w - 1, h - 1)
#Spiel starten
isRunning = True
score = 0
gameloop()
player.on_chat(„start“, startTetris)
def makeBoard(w, h):
global playerY
global playerZ
global buildGlass
#Plattform bauen
blocks.fill(GLASS, pos(-1, -2, -1), pos(1, -2, 1))
blocks.fill(blocks.block_by_name("scaffolding"), pos(-1, -1, -1), pos(1, -1, 1))
blocks.fill(GLASS_PANE, pos(-1, 0, -1), pos(1, 0, -1))
blocks.fill(GLASS_PANE, pos(-1, 0, 1), pos(1, 0, 1))
blocks.place(GLASS_PANE, pos(-1, 0, 0))
blocks.place(GLASS_PANE, pos(1, 0, 0))
#Bildschirm bauen
n = Math.round(w / 2)
o = Math.round(w/2%1)
blocks.fill(BLACK_CONCRETE, pos(-n, -playerY, playerZ+1), pos(n+o, h-playerY, playerZ+1))
blocks.fill(POLISHED_ANDESITE, pos(-n-1, -1-playerY, playerZ+1), pos(-n-1, h+1-playerY, playerZ-1))
blocks.fill(POLISHED_ANDESITE, pos(n+o+1, -1-playerY, playerZ+1), pos(n+o+1, h+1-playerY, playerZ-1))
blocks.fill(POLISHED_ANDESITE, pos(-n-1, -1-playerY, playerZ+1), pos(n+o+1, -1-playerY, playerZ-1))
blocks.fill(POLISHED_ANDESITE, pos(-n-1, h+1-playerY, playerZ+1), pos(n+o+1, h+1-playerY, playerZ-1))
blocks.fill(AIR, pos(-n, -playerY, playerZ-1), pos(n+o, h-playerY, playerZ))
if buildGlass:
blocks.fill(GLASS, pos(-n, -playerY, playerZ-1), pos(n+o, h-playerY, playerZ-1))
def stopTetris():
global isRunning #Aus gameloop() ausbrechen isRunning = False
player.on_chat(„stop“, stopTetris)
def getPiece():
global piece
global color
global pieceX
global unusedPieces
#Eines der Tetrominos wählen
random = Math.round(Math.random()*unusedPieces.length)
n = unusedPieces[random]
if unusedPieces.length < 1:
unusedPieces = range(7)
else:
unusedPieces.remove(n)
if n < 1:
#I
piece = [[0,1,0,0],[0,1,0,0],[0,1,0,0],[0,1,0,0]]
color = LIGHT_BLUE_WOOL
elif n < 2:
#O
piece = [[1,1],[1,1]]
color = YELLOW_WOOL
pieceX = pieceX + 1
elif n < 3:
#T
piece = [[0,1,0],[1,1,0],[0,1,0]]
color = PURPLE_WOOL
elif n < 4:
#S
piece = [[1,0,0],[1,1,0],[0,1,0]]
color = RED_WOOL
elif n < 5:
#2
piece = [[0,1,0],[1,1,0],[1,0,0]]
color = LIME_WOOL
elif n < 6:
#L
piece = [[1,1,0],[0,1,0],[0,1,0]]
color = ORANGE_WOOL
elif n < 7:
#J
piece = [[0,1,0],[0,1,0],[1,1,0]]
color = BLUE_WOOL
#Durchgehend wiederholende Funktion die Spiel „steuert“
def gameloop():
global isRunning
frame = 0
#Wiederholen bis Spieler "stop" schreibt
while isRunning:
#Bei Bewegung den Tetromino bewegen
movedDirection = playerMoved()
if movedDirection[0] != "":
movePiece(movedDirection[0], movedDirection[1])
player.teleport(origin)
#Alle 20 Durchläufe den Tetromino nach unten bewegen
if frame % 20 == 0:
moveDown()
frame += 1
#Bewegen der Tetrominos
def playerMoved():
#neue und alte Position vergleichen
cPos = player.position()
if origin.to_string() == cPos.to_string():
return ["", ""]
else:
#Richtung bestimmen
x = origin.get_value(Axis.X) - cPos.get_value(Axis.X)
y = origin.get_value(Axis.Y) - cPos.get_value(Axis.Y)
z = origin.get_value(Axis.Z) - cPos.get_value(Axis.Z)
if x < 0:
return ["x", "+"]
elif x > 0:
return ["x", "-"]
elif y != 0:
return ["y", "+"]
elif z < 0:
return ["z", "+"]
else:
return ["z", "-"]
def movePiece(direction, sign):
global piece
#Je nach Richtung richtige Bewegung ausführen
if direction == "x" and sign == "-":
move(-1)
elif direction == "x" and sign == "+":
move(1)
elif direction == "y":
moveToBottom()
elif direction == "z" and sign == "-":
rotateLeft()
else:
rotateRight()
def move(n):
global piece
global pieceX
global pieceY
#X Wert des Tetrominos ändern
newX = pieceX + n
if not checkCollisions(piece, newX, pieceY, False):
checkCollisions(piece, newX, pieceY, True)
def moveDown():
global piece global pieceX global pieceY #Y Wert des Tetrominos ändern newY = pieceY - 1 checkCollisions(piece, pieceX, newY, True)
def moveToBottom():
global piece
global pieceX
global pieceY
global board
global playerY
global playerZ
#Y Wert des Tetrominos senken bis Kollision stattfindet
newY = pieceY
while not checkCollisions(piece, pieceX, newY, False):
newY = newY - 1
player.execute("fill ~" + str(-w/2-1) + " ~" + str(-playerY) + " ~" + str(playerZ) + " ~" + str(w/2+1) + " ~" + str(h-playerY) + " ~" + str(playerZ) + " air 0 replace wool " + id(color))
pieceY = newY + 1
placePiece()
def rotateLeft():
global piece
global pieceX
global pieceY
tempPiece = []
newPiece = []
for i in range(piece.length):
tr = range(piece.length)
tempPiece[i] = tr
newPiece[i] = tr
for j in range(piece.length):
tempPiece[i][j] = 0
newPiece[i][j] = 0
newPiece = piece
tPiece = piece
#gedrehtes Tetromino in neue Liste speichern
for i in range(piece.length):
for j in range(piece.length):
tempPiece[i][j] = tPiece[i][piece.length-1-j]
for i in range(piece.length):
for j in range(piece.length):
newPiece[j][i] = tempPiece[i][j]
player.execute("fill ~" + str(-w/2) + " ~" + str(-playerY) + " ~" + str(playerZ) + " ~" + str(w/2) + " ~" + str(h-playerY) + " ~" + str(playerZ+1) + " air 0 replace wool " + id(color))
checkCollisions(newPiece, pieceX, pieceY, True)
def rotateRight():
global piece
global pieceX
global pieceY
tempPiece = []
newPiece = []
for i in range(piece.length):
tr = range(piece.length)
tempPiece[i] = tr
newPiece[i] = tr
for j in range(piece.length):
tempPiece[i][j] = 0
newPiece[i][j] = 0
newPiece = piece
#gedrehtes Tetromino in neue Liste speichern
for i in range(piece.length):
for j in range(piece.length):
tempPiece[j][i] = piece[i][j]
for i in range(tempPiece.length):
for j in range(tempPiece.length):
newPiece[i][tempPiece.length-1-j] = tempPiece[i][j]
player.execute("fill ~" + str(-w/2) + " ~" + str(-playerY) + " ~" + str(playerZ) + " ~" + str(w/2) + " ~" + str(h-playerY) + " ~" + str(playerZ-1) + " air 0 replace wool " + id(color))
checkCollisions(newPiece, pieceX, pieceY, True)
def checkCollisions(newPiece, newX, newY, proceed):
global board
#Kollisionen finden und testen ob Tetromino zuunterst ist
#Ohne tempPiece entsteht Error, weil type von newPiece nicht bekannt ist
tempPiece = [[0]]
tempPiece = newPiece
collided = False
bottom = False
walls = False
for i in range(newPiece.length):
for j in range(newPiece.length):
if newPiece[i][j] == 1:
if i + newX >= board.length or i + newX < 0:
walls = True
elif board[i + newX][j + newY] == 1:
collided = True
elif j + newY < 0:
bottom = True
if proceed and not walls :
if bottom:
placePiece()
elif not collided:
updatePiece(newPiece, newX, newY)
else:
placePiece()
elif bottom or collided or walls:
return(True)
return(False)
#Funktionen zum Ändern des Bildschirms der „Konsole“
def updatePiece(newPiece, newX, newY):
global board
global piece
global pieceX
global pieceY
global h
global playerY
global playerZ
global color
player.execute("fill ~" + str(-w/2-1) + " ~" + str(-playerY) + " ~" + str(playerZ) + " ~" + str(w/2+1) + " ~" + str(h-playerY) + " ~" + str(playerZ) + " air 0 replace wool " + id(color))
for i in range(newPiece.length):
for j in range(newPiece.length):
if newPiece[i][j] == 1:
if newY + j < h:
blocks.place(color, positions.add(origin, pos(-w/2+newX+i, newY+j-playerY, playerZ)))
piece = newPiece
pieceX = newX
pieceY = newY
def placePiece():
global board
global piece
global pieceX
global pieceY
global score
global isRunning
#Tetromino zur "board" Liste hinzufügen
for i in range(piece.length):
for j in range(piece.length):
if piece[i][j] == 1:
board[i + pieceX][j + pieceY] = 1
if pieceY + j < h:
blocks.place(placeColor(color), positions.add(origin, pos(-w/2+pieceX+i, pieceY+j-playerY, playerZ)))
if pieceY + j >= h:
isRunning = False
if isRunning:
#Komplette Reihen entfernen
removeRow(i)
#Neues Tetromino generieren
score = score + 1
pieceX = Math.round(w/2) - 2
pieceY = h - 1
getPiece()
else:
player.say("Zu langsam ☹")
player.say("score: " + str(score))
def removeRow(j):
global board
global w
global h
y = 0
for _ in range(h):
complete = 1
for i in range(w):
complete = complete * board[i][y]
if complete == 1:
#alles über der Reihe nach unten schieben
for k in range(w):
for l in range(y, h):
board[k][l] = board[k][l+1]
for l in range(y, h-1):
blocks.clone(positions.add(origin, pos(-w/2, l+1-playerY, playerZ)), positions.add(origin, pos(w/2, l+1-playerY, playerZ)), positions.add(origin, pos(-w/2, l-playerY, playerZ)), CloneMask.REPLACE, CloneMode.NORMAL)
for k in range(w-2):
board[k][h-1]=0
blocks.fill(AIR, positions.add(origin, pos(-w/2,h-1-playerY, playerZ)), positions.add(origin, pos(w/2-1, h-1-playerY, playerZ)))
else:
y = y + 1
def placeColor(color):
if color == LIGHT_BLUE_WOOL:
return(LIGHT_BLUE_CONCRETE)
elif color == YELLOW_WOOL:
return(YELLOW_CONCRETE)
elif color == PURPLE_WOOL:
return(PURPLE_CONCRETE)
elif color == LIME_WOOL:
return(LIME_CONCRETE)
elif color == RED_WOOL:
return(RED_CONCRETE)
elif color == ORANGE_WOOL:
return(ORANGE_CONCRETE)
else:
return(BLUE_CONCRETE)
def id(color):
if color == LIGHT_BLUE_WOOL:
return 3
elif color == YELLOW_WOOL:
return 4
elif color == PURPLE_WOOL:
return 10
elif color == LIME_WOOL:
return 5
elif color == RED_WOOL:
return 14
elif color == ORANGE_WOOL:
return 1
else:
return 11