diff --git a/README.md b/README.md index b2a08a4..83ee78c 100644 --- a/README.md +++ b/README.md @@ -89,7 +89,7 @@ print("pos: x:{},y:{},z:{}".format(pos.x,pos.y,pos.z)) ``` Use your faverate python editor to open the sample1.py file. -When you install python, it come with a python editor call IDLE. +When you install python, it come with a python editor call IDLE.j ### 1.2. Frequently used `mcpi` commands diff --git a/documents/2_LearnPythonWithMineCraft/2.1_Understand_the_coordinates_of_minecraft.md b/documents/2_LearnPythonWithMineCraft/2.1_Understand_the_coordinates_of_minecraft.md index f2821ad..46f3890 100644 --- a/documents/2_LearnPythonWithMineCraft/2.1_Understand_the_coordinates_of_minecraft.md +++ b/documents/2_LearnPythonWithMineCraft/2.1_Understand_the_coordinates_of_minecraft.md @@ -6,7 +6,7 @@ ## 2.1 Understand the coordinates of minecraft -Minecraft coordinates is different than what we learn from geomestry. you need keep below picture in mind when you do the minecraft coding. +Minecraft coordinates is different than what we learn from geometry. you need keep below picture in mind when you do the minecraft coding. ![coordinates of minecraft](../minecraft_Coordinates.png) For basic python syntax, pleas check [Python syntax](https://www.w3schools.com/python/python_syntax.asp) for details. @@ -93,5 +93,20 @@ Try place a watermelon beside you. mc.setBlock(x,y,z,103) ``` +#### - [Mission-1.6] Use Python place multiple blocks point direction of x,y,z + +Use python code to place color block like below + +```python +mc=Minecraft.create(serverAddress,pythonApiPort,playerName) +pos=mc.player.getTilePos() +(x,y,z)=pos=mc.player.getPos() + +mc.setBlock(x+1,y,z,block.WOOL_GREEN) +mc.setBlock(x+2,y,z,block.WOOL_RED) +mc.setBlock(x+3,y,z,block.WOOL_BLUE) +``` + +![xyz](./../xyz.jpg) [back to main](../../README.md) diff --git a/documents/2_LearnPythonWithMineCraft/2.2_Use_for_loop_to_stack_blocks.md b/documents/2_LearnPythonWithMineCraft/2.2_Use_for_loop_to_stack_blocks.md index cd55ab6..aa7bcfc 100644 --- a/documents/2_LearnPythonWithMineCraft/2.2_Use_for_loop_to_stack_blocks.md +++ b/documents/2_LearnPythonWithMineCraft/2.2_Use_for_loop_to_stack_blocks.md @@ -70,9 +70,9 @@ for k in range(0,5): ``` -### - [Challenge] [Mission-2.5] Build a 10x10X10 pyramid in Minecraft +### - [Challenge] [Mission-2.5] Build a 10x10X5 pyramid in Minecraft -Modified your code in mission-2.4, build a 10X10X10 pyramid. +Modified your code in mission-2.4, build a 10X10X5 pyramid. please show you work. [back to main](../../README.md) diff --git a/documents/xyz.jpg b/documents/xyz.jpg new file mode 100644 index 0000000..f9a5aaa Binary files /dev/null and b/documents/xyz.jpg differ diff --git a/samples/dna.py b/samples/dna.py new file mode 100644 index 0000000..253c0ec --- /dev/null +++ b/samples/dna.py @@ -0,0 +1,47 @@ + +from functions.drawing import * +from random import choice +import mcpi_e.minecraft as minecraft +from mcpi_e.block import * + +address="server" +name="stoneskin" +mc = minecraft.Minecraft.create(address,4712,name) + +drawing = Drawing(mc) + +pos = mc.player.getTilePos() +radius = 10 +A = WOOL_ORANGE = Block(WOOL.id, 1) +C = WOOL_GREEN = Block(WOOL.id, 13) +G= WOOL_BLUE = Block(WOOL.id, 11) +T= WOOL_RED = Block(WOOL.id, 14) + + +blocks = { "A":(A,T), "C":(C,G), "T":(T,A), "G":(G,C) } +# sequence taken from somewhere in chromosome 5, retrieved via Wolfram Alpha +sequence = "CAAAAGTGTGGGGAAATTAATTTGGGAATTACTCTCCTCATTGAAAAATATCTCATTTGCTAAAATAAGACAGTAAAACAGTACAGTTTAAATATTTATAAAAATAGGAAAGTTTGGCAAAAAGAGAGGAGTACACACCTGTGACTACTGAGTTGCTGTGAAAATTTCATTTCCTGATACAAAATTGTCTAAAGCACTTG" + +def getPair(i): + return blocks[sequence[-i-1]] + +prev = None +skip = 2 +for y in range(240): + theta = y * pi / (skip*10) + y1 = pos.y + y + x1 = pos.x - radius * cos(theta) + x2 = pos.x + radius * cos(theta) + z1 = pos.z + radius * sin(theta) + z2 = pos.z - radius * sin(theta) + if y % skip == 0: + pair = getPair(y//skip) + drawing.penwidth(1) + drawing.line(x1,y1,z1,pos.x,y1,pos.z,pair[0]) + drawing.line(x2,y1,z2,pos.x,y1,pos.z,pair[1]) + + if prev is not None: + drawing.penwidth(2) + drawing.line(prev[0],prev[1],prev[2],x1,y1,z1,block.WOOL_WHITE) + drawing.line(prev[3],prev[4],prev[5],x2,y1,z2,block.WOOL_WHITE) + prev = x1,y1,z1,x2,y1,z2 diff --git a/samples/donut.py b/samples/donut.py new file mode 100644 index 0000000..89497af --- /dev/null +++ b/samples/donut.py @@ -0,0 +1,30 @@ +from mcpi_e.minecraft import Minecraft +from mcpi_e import block +from time import sleep +from random import * +from math import * + +def draw_donut(mcx,mcy,mcz,R,r,mcblock): + for x in range(-R-r,R+r): + for y in range(-R-r,R+r): + xy_dist = sqrt(x**2 + y**2) + if (xy_dist > 0): + ringx = x / xy_dist * R # nearest point on major ring + ringy = y / xy_dist * R + ring_dist_sq = (x-ringx)**2 + (y-ringy)**2 + + for z in range(-R-r,R+r): + if (ring_dist_sq + z**2 <= r**2): + mc.setBlock(mcx+x, mcy+z, mcz+y, mcblock) + +serverAddress="server" # change to your minecraft server +playerName ="stoneskin" +pythonApiPort=4712 + +mc=Minecraft.create(serverAddress,pythonApiPort,playerName) +playerPos=mc.player.getTilePos() + +draw_donut(playerPos.x, playerPos.y + 9, playerPos.z, 18, 9, block.GLASS) +mc.postToChat("Glass donut done") +draw_donut(playerPos.x, playerPos.y + 9, playerPos.z, 18, 6, block.WATER_STATIONARY) +mc.postToChat("Water donut done") \ No newline at end of file diff --git a/samples/egg.py b/samples/egg.py new file mode 100644 index 0000000..ae4c0d9 --- /dev/null +++ b/samples/egg.py @@ -0,0 +1,41 @@ +import sys +import mcpi_e.block as block +from mcpi_e.minecraft import Minecraft +from math import * +Block = block.Block + +def egg(block=block.GOLD_BLOCK, h=40, a=2.5, b=1, c=0.1): + for y in range(0,h+1): + l = y / float(h) + # Formula from: http://www.jolyon.co.uk/myresearch/image-analysis/egg-shape-modelling/ + r = h*a*exp((-0.5*l*l+c*l-.5*c*c)/(b*b))*sqrt(1-l)*sqrt(l)/(pi*b) + r2 = r*r + for x in range(-h,h+1): + for z in range(-h,h+1): + myr2 = x*x + z*z + if myr2 <= r2: + if x==0 and z==0: + theta = 0 + else: + theta = atan2(z,x) + yield (x,y,z,block,theta) + +address="server" +name="stoneskin" +mc = Minecraft.create(address,4712,name) + + +if len(sys.argv) >= 2: + height = int(sys.argv[1]) +else: + height = 50 + +if len(sys.argv) >= 3: + material = Block.byName(sys.argv[2]) +else: + material = block.GOLD_BLOCK + +pos = mc.player.getPos() + +for (x,y,z,block,theta) in egg(h=height,block=material): + mc.setBlock(x+pos.x,y+pos.y,z+pos.z,block) diff --git a/samples/functions/drawing.py b/samples/functions/drawing.py new file mode 100644 index 0000000..58eed60 --- /dev/null +++ b/samples/functions/drawing.py @@ -0,0 +1,522 @@ +# +# Code by Alexander Pruss and under the MIT license +# + +import mcpi_e.minecraft as minecraft +import mcpi_e.block as block +from mcpi_e.entity import * +from math import * +from numbers import Number,Integral + +class V3(tuple): + def __new__(cls,*args): + if len(args) == 1: + return tuple.__new__(cls,tuple(*args)) + else: + return tuple.__new__(cls,args) + + def dot(self,other): + return self[0]*other[0]+self[1]*other[1]+self[2]*other[2] + + @property + def x(self): + return self[0] + + @property + def y(self): + return self[1] + + @property + def z(self): + return self[2] + + def __add__(self,other): + other = tuple(other) + return V3(self[0]+other[0],self[1]+other[1],self[2]+other[2]) + + def __radd__(self,other): + other = tuple(other) + return V3(self[0]+other[0],self[1]+other[1],self[2]+other[2]) + + def __sub__(self,other): + other = tuple(other) + return V3(self[0]-other[0],self[1]-other[1],self[2]-other[2]) + + def __rsub__(self,other): + other = tuple(other) + return V3(other[0]-self[0],other[1]-self[1],other[2]-self[2]) + + def __neg__(self): + return V3(-self[0],-self[1],-self[2]) + + def __pos__(self): + return self + + def len2(self): + return self[0]*self[0]+self[1]*self[1]+self[2]*self[2] + + def __abs__(self): + return sqrt(self.len2()) + + def __div__(self,other): + if isinstance(other,Number): + y = float(other) + return V3(self[0]/y,self[1]/y,self[2]/y) + else: + return NotImplemented + + def __mul__(self,other): + if isinstance(other,Number): + return V3(self[0]*other,self[1]*other,self[2]*other) + else: + other = tuple(other) + # cross product + return V3(self[1]*other[2]-self[2]*other[1],self[2]*other[0]-self[0]*other[2],self[0]*other[1]-self[1]*other[0]) + + def __rmul__(self,other): + return self.__mul__(other) + + def __repr__(self): + return "V3"+repr(tuple(self)) + + def ifloor(self): + return V3(int(floor(self[0])),int(floor(self[1])),int(floor(self[2]))) + + def iceil(self): + return V3(int(ceil(self[0])),int(ceil(self[1])),int(ceil(self[2]))) + +TO_RADIANS = pi / 180. +TO_DEGREES = 180. / pi +ICOS = [1,0,-1,0] +ISIN = [0,1,0,-1] + +def makeMatrix(compass,vertical,roll): + m0 = matrixMultiply(yawMatrix(compass), pitchMatrix(vertical)) + return matrixMultiply(m0, rollMatrix(roll)) + +def applyMatrix(m,v): + if m is None: + return v + else: + return V3(m[i][0]*v[0]+m[i][1]*v[1]+m[i][2]*v[2] for i in range(3)) + +def matrixDistanceSquared(m1,m2): + d2 = 0. + for i in range(3): + for j in range(3): + d2 += (m1[i][j]-m2[i][j])**2 + return d2 + +def iatan2(y,x): + """One coordinate must be zero""" + if x == 0: + return 90 if y > 0 else -90 + else: + return 0 if x > 0 else 180 + +def icos(angleDegrees): + """Calculate a cosine of an angle that must be a multiple of 90 degrees""" + return ICOS[(angleDegrees % 360) // 90] + +def isin(angleDegrees): + """Calculate a sine of an angle that must be a multiple of 90 degrees""" + return ISIN[(angleDegrees % 360) // 90] + +def matrixMultiply(a,b): + c = [[0,0,0],[0,0,0],[0,0,0]] + for i in range(3): + for j in range(3): + c[i][j] = a[i][0]*b[0][j] + a[i][1]*b[1][j] + a[i][2]*b[2][j] + return c + +def yawMatrix(angleDegrees): + if isinstance(angleDegrees, Integral) and angleDegrees % 90 == 0: + return [[icos(angleDegrees), 0, -isin(angleDegrees)], + [0, 1, 0], + [isin(angleDegrees), 0, icos(angleDegrees)]] + else: + theta = angleDegrees * TO_RADIANS + return [[cos(theta), 0., -sin(theta)], + [0., 1., 0.], + [sin(theta), 0., cos(theta)]] + +def rollMatrix(angleDegrees): + if isinstance(angleDegrees, Integral) and angleDegrees % 90 == 0: + return [[icos(angleDegrees), -isin(angleDegrees), 0], + [isin(angleDegrees), icos(angleDegrees),0], + [0, 0, 1]] + else: + theta = angleDegrees * TO_RADIANS + return [[cos(theta), -sin(theta), 0.], + [sin(theta), cos(theta),0.], + [0., 0., 1.]] + +def pitchMatrix(angleDegrees): + if isinstance(angleDegrees, Integral) and angleDegrees % 90 == 0: + return [[1, 0, 0], + [0, icos(angleDegrees),isin(angleDegrees)], + [0, -isin(angleDegrees),icos(angleDegrees)]] + else: + theta = angleDegrees * TO_RADIANS + return [[1., 0., 0.], + [0., cos(theta),sin(theta)], + [0., -sin(theta),cos(theta)]] + +def get2DTriangle(a,b,c): + """get the points of the 2D triangle""" + minX = {} + maxX = {} + + for line in (traverse2D(a,b), traverse2D(b,c), traverse2D(a,c)): + for p in line: + minX0 = minX.get(p[1]) + if minX0 == None: + minX[p[1]] = p[0] + maxX[p[1]] = p[0] + yield(p) + elif p[0] < minX0: + for x in range(p[0],minX0): + yield(x,p[1]) + minX[p[1]] = p[0] + else: + maxX0 = maxX[p[1]] + if maxX0 < p[0]: + for x in range(maxX0,p[0]): + yield(x,p[1]) + maxX[p[1]] = p[0] + +def getFace(vertices): + if len(vertices) < 1: + raise StopIteration + if len(vertices) <= 2: + for p in traverse(V3(vertices[0]), V3(vertices[1])): + yield p + v0 = V3(vertices[0]) + for i in range(2,len(vertices)): + for p in traverse(V3(vertices[i-1]), V3(vertices[i])): + for q in traverse(p, v0): + yield q + +def getTriangle(p1, p2, p3): + """ + Note that this will return many duplicate poitns + """ + p1,p2,p3 = V3(p1),V3(p2),V3(p3) + + for u in traverse(p2,p3): + for w in traverse(p1,u): + yield w + +def frac(x): + return x - floor(x) + +def traverse2D(a,b): + """ + equation of line: a + t(b-a), t from 0 to 1 + Based on Amantides and Woo's ray traversal algorithm with some help from + http://stackoverflow.com/questions/12367071/how-do-i-initialize-the-t-variables-in-a-fast-voxel-traversal-algorithm-for-ray + """ + + inf = float("inf") + + if b[0] == a[0]: + if b[1] == a[1]: + yield (int(floor(a[0])),int(floor(a[1]))) + return + tMaxX = inf + tDeltaX = 0 + else: + tDeltaX = 1./abs(b[0]-a[0]) + tMaxX = tDeltaX * (1. - frac(a[0])) + + if b[1] == a[1]: + tMaxY = inf + tDeltaY = 0 + else: + tDeltaY = 1./abs(b[1]-a[1]) + tMaxY = tDeltaY * (1. - frac(a[1])) + + endX = int(floor(b[0])) + endY = int(floor(b[1])) + x = int(floor(a[0])) + y = int(floor(a[1])) + if x <= endX: + stepX = 1 + else: + stepX = -1 + if y <= endY: + stepY = 1 + else: + stepY = -1 + + yield (x,y) + if x == endX: + if y == endY: + return + tMaxX = inf + if y == endY: + tMaxY = inf + + while True: + if tMaxX < tMaxY: + x += stepX + yield (x,y) + if x == endX: + tMaxX = inf + else: + tMaxX += tDeltaX + else: + y += stepY + yield (x,y) + if y == endY: + tMaxY = inf + else: + tMaxY += tDeltaY + + if tMaxX == inf and tMaxY == inf: + return + +def traverse(a,b): + """ + equation of line: a + t(b-a), t from 0 to 1 + Based on Amantides and Woo's ray traversal algorithm with some help from + http://stackoverflow.com/questions/12367071/how-do-i-initialize-the-t-variables-in-a-fast-voxel-traversal-algorithm-for-ray + """ + + inf = float("inf") + + if b.x == a.x: + if b.y == a.y and b.z == a.z: + yield a.ifloor() + return + tMaxX = inf + tDeltaX = 0 + else: + tDeltaX = 1./abs(b.x-a.x) + tMaxX = tDeltaX * (1. - frac(a.x)) + + if b.y == a.y: + tMaxY = inf + tDeltaY = 0 + else: + tDeltaY = 1./abs(b.y-a.y) + tMaxY = tDeltaY * (1. - frac(a.y)) + + if b.z == a.z: + tMaxZ = inf + tDeltaZ = 0 + else: + tDeltaZ = 1./abs(b.z-a.z) + tMaxZ = tDeltaZ * (1. - frac(a.z)) + + end = b.ifloor() + x = int(floor(a.x)) + y = int(floor(a.y)) + z = int(floor(a.z)) + if x <= end.x: + stepX = 1 + else: + stepX = -1 + if y <= end.y: + stepY = 1 + else: + stepY = -1 + if z <= end.z: + stepZ = 1 + else: + stepZ = -1 + + yield V3(x,y,z) + + if x == end.x: + if y == end.y and z == end.z: + return + tMaxX = inf + if y == end.y: + tMaxY = inf + if z == end.z: + tMaxZ = inf + + while True: + if tMaxX < tMaxY: + if tMaxX < tMaxZ: + x += stepX + yield V3(x,y,z) + if x == end.x: + tMaxX = inf + else: + tMaxX += tDeltaX + else: + z += stepZ + yield V3(x,y,z) + if z == end.z: + tMaxZ = inf + else: + tMaxZ += tDeltaZ + else: + if tMaxY < tMaxZ: + y += stepY + yield V3(x,y,z) + if y == end.y: + tMaxY = inf + else: + tMaxY += tDeltaY + else: + z += stepZ + yield V3(x,y,z) + if z == end.z: + tMaxZ = inf + else: + tMaxZ += tDeltaZ + + if tMaxX == inf and tMaxY == inf and tMaxZ == inf: + return + +# Brasenham's algorithm +def getLine(x1, y1, z1, x2, y2, z2): + line = [] + x1 = int(floor(x1)) + y1 = int(floor(y1)) + z1 = int(floor(z1)) + x2 = int(floor(x2)) + y2 = int(floor(y2)) + z2 = int(floor(z2)) + point = [x1,y1,z1] + dx = x2 - x1 + dy = y2 - y1 + dz = z2 - z1 + x_inc = -1 if dx < 0 else 1 + l = abs(dx) + y_inc = -1 if dy < 0 else 1 + m = abs(dy) + z_inc = -1 if dz < 0 else 1 + n = abs(dz) + dx2 = l << 1 + dy2 = m << 1 + dz2 = n << 1 + + if l >= m and l >= n: + err_1 = dy2 - l + err_2 = dz2 - l + for i in range(0,l-1): + line.append(V3(point[0],point[1],point[2])) + if err_1 > 0: + point[1] += y_inc + err_1 -= dx2 + if err_2 > 0: + point[2] += z_inc + err_2 -= dx2 + err_1 += dy2 + err_2 += dz2 + point[0] += x_inc + elif m >= l and m >= n: + err_1 = dx2 - m; + err_2 = dz2 - m; + for i in range(0,m-1): + line.append(V3(point[0],point[1],point[2])) + if err_1 > 0: + point[0] += x_inc + err_1 -= dy2 + if err_2 > 0: + point[2] += z_inc + err_2 -= dy2 + err_1 += dx2 + err_2 += dz2 + point[1] += y_inc + else: + err_1 = dy2 - n; + err_2 = dx2 - n; + for i in range(0, n-1): + line.append(V3(point[0],point[1],point[2])) + if err_1 > 0: + point[1] += y_inc + err_1 -= dz2 + if err_2 > 0: + point[0] += x_inc + err_2 -= dz2 + err_1 += dy2 + err_2 += dx2 + point[2] += z_inc + line.append(V3(point[0],point[1],point[2])) + if point[0] != x2 or point[1] != y2 or point[2] != z2: + line.append(V3(x2,y2,z2)) + return line + + +class Drawing: + TO_RADIANS = pi / 180. + TO_DEGREES = 180. / pi + + def __init__(self,mc=None): + if mc is not None: + self.mc = mc + else: + self.mc = minecraft.Minecraft() + self.width = 1 + self.nib = [(0,0,0)] + + def penwidth(self,w): + self.width = int(w) + if self.width == 0: + self.nib = [] + elif self.width == 1: + self.nib = [(0,0,0)] + elif self.width == 2: + self.nib = [] + for x in range(-1,1): + for y in range(0,2): + for z in range(-1,1): + self.nib.append((x,y,z)) + else: + self.nib = [] + r2 = self.width * self.width / 4. + for x in range(-self.width//2 - 1,self.width//2 + 1): + for y in range(-self.width//2 - 1, self.width//2 + 1): + for z in range(-self.width//2 -1, self.width//2 + 1): + if x*x + y*y + z*z <= r2: + self.nib.append((x,y,z)) + + def point(self, x, y, z, block): + for p in self.nib: + self.mc.setBlock(x+p[0],y+p[1],z+p[2],block) + + def face(self, vertices, block): + self.drawPoints(getFace(vertices), block) + + def line(self, x1,y1,z1, x2,y2,z2, block): + self.drawPoints(getLine(x1,y1,z1, x2,y2,z2), block) + + def drawPoints(self, points, block): + if self.width == 1: + done = set() + for p in points: + if p not in done: + self.mc.setBlock(p, block) + done.add(p) + else: + done = set() + for p in points: + for point in self.nib: + x0 = p[0]+point[0] + y0 = p[1]+point[1] + z0 = p[2]+point[2] + if (x0,y0,z0) not in done: + self.mc.setBlock(x0,y0,z0,block) + done.add((x0,y0,z0)) + +if __name__ == "__main__": + d = Drawing() + pos = d.mc.player.getPos() + d.face([(pos.x,pos.y,pos.z),(pos.x+20,pos.y+20,pos.z),(pos.x+20,pos.y+20,pos.z+20), + (pos.x,pos.y,pos.z+20)], block.GLASS) + n = 20 + for t in range(0,n): + (x1,z1) = (100*cos(t*2*pi/n),80*sin(t*2*pi/n)) + for p in traverse(V3(pos.x,pos.y-1,pos.z),V3(pos.x+x1,pos.y-1,pos.z+z1)): + d.mc.setBlock(p,block.OBSIDIAN) + n = 40 + vertices = [] + for t in range(0,n): + (x1,z1) = (100*cos(t*2*pi/n),80*sin(t*2*pi/n)) + vertices.append((pos.x+x1,pos.y,pos.z+z1)) + d.face(vertices, block.STAINED_GLASS_BLUE) \ No newline at end of file diff --git a/samples/pixel copy.py b/samples/pixel copy.py new file mode 100644 index 0000000..8edc2a2 --- /dev/null +++ b/samples/pixel copy.py @@ -0,0 +1,24 @@ +import mcpi_e.minecraft as minecraft +serverAddress="192.168.1.155" # change to your minecraft server +port=4711 +name="stoneskin" +mc = minecraft.Minecraft.create(serverAddress,port,name) + +pos = mc.player.getTilePos() +x, y, z = pos.x, pos.y, pos.z + +blocks = [[35, 35, 22, 22, 22, 22, 35, 35], + [35, 22, 35, 35, 35, 35, 22, 35], + [22, 35, 22, 35, 35, 22, 35, 22], + [22, 35, 35, 35, 35, 35, 35, 22], + [22, 35, 22, 35, 35, 22, 35, 22], + [22, 35, 35, 22, 22, 35, 35, 22], + [35, 22, 35, 35, 35, 35, 22, 35], + [35, 35, 22, 22, 22, 22, 35, 35]] + +for row in reversed(blocks): + for block in row: + mc.setBlock(x, y, z, block) + x += 1 + y += 1 + x = pos.x \ No newline at end of file diff --git a/samples/pixel.py b/samples/pixel.py new file mode 100644 index 0000000..8edc2a2 --- /dev/null +++ b/samples/pixel.py @@ -0,0 +1,24 @@ +import mcpi_e.minecraft as minecraft +serverAddress="192.168.1.155" # change to your minecraft server +port=4711 +name="stoneskin" +mc = minecraft.Minecraft.create(serverAddress,port,name) + +pos = mc.player.getTilePos() +x, y, z = pos.x, pos.y, pos.z + +blocks = [[35, 35, 22, 22, 22, 22, 35, 35], + [35, 22, 35, 35, 35, 35, 22, 35], + [22, 35, 22, 35, 35, 22, 35, 22], + [22, 35, 35, 35, 35, 35, 35, 22], + [22, 35, 22, 35, 35, 22, 35, 22], + [22, 35, 35, 22, 22, 35, 35, 22], + [35, 22, 35, 35, 35, 35, 22, 35], + [35, 35, 22, 22, 22, 22, 35, 35]] + +for row in reversed(blocks): + for block in row: + mc.setBlock(x, y, z, block) + x += 1 + y += 1 + x = pos.x \ No newline at end of file diff --git a/samples/rainbow.py b/samples/rainbow.py index 6a37a45..6db18e9 100644 --- a/samples/rainbow.py +++ b/samples/rainbow.py @@ -9,9 +9,10 @@ address="127.0.0.1" # change to your minecraft server name ="you username" -colors = [14, 1, 4, 5, 3, 11, 10] +mc = minecraft.Minecraft.create(address,4712,name) + -mc = minecraft.Minecraft.create(address,4711,name) +colors = [14, 1, 4, 5, 3, 11, 10] playerPos=mc.player.getTilePos() height=50 diff --git a/samples/spiral.py b/samples/spiral.py new file mode 100644 index 0000000..3bdbeb9 --- /dev/null +++ b/samples/spiral.py @@ -0,0 +1,27 @@ +import mcpi_e.minecraft as minecraft +import mcpi_e.block as block +import math + +def draw_horizontal_disc(cx, cy, cz, radius, block_type, meta): + for x in range(-radius, radius): + for z in range(-radius, radius): + if (x**2 + z**2 <= radius**2): + mc.setBlock(cx + x, cy, cz + z, block_type, meta) + +def draw_spiral(mcx,mcy,mcz,major_radius,minor_radius,height,period,phase,block_type,meta): + for y in range(0,height - 1): + theta = math.pi * 2 * y/period + phase + circle_center_x = mcx + major_radius*math.cos(theta) + circle_center_z = mcz + major_radius*math.sin(theta) + draw_horizontal_disc(circle_center_x, mcy + y, circle_center_z, minor_radius, block_type, meta) + +address="127.0.0.1" # change to your minecraft server +name ="you username" +mc = minecraft.Minecraft.create(address,4712,name) + + +playerPos = mc.player.getPos() + +draw_spiral(playerPos.x, playerPos.y, playerPos.z, 18, 10, 20, 5, 0, block.GOLD_BLOCK, 0) +draw_spiral(playerPos.x, playerPos.y, playerPos.z, 18, 10, 20, 5, math.pi, block.DIAMOND_BLOCK, 0) +mc.postToChat("Spiral done") \ No newline at end of file diff --git a/samples/tree.py b/samples/tree.py new file mode 100644 index 0000000..c93eb90 --- /dev/null +++ b/samples/tree.py @@ -0,0 +1,77 @@ +import time +from mcpi_e.minecraft import Minecraft + +address="192.168.1.155"#if not pass address, it will be localhost +port=4711 #default port for RaspberryJuice plugin is 4711 +player="stoneskin2020" +mc = Minecraft.create(address,port,player) + + +class Building(object): + def __init__(self, x, y, z, width, height, depth): + self.x = x + self.y = y + self.z = z + + self.width = width + self.height = height + self.depth = depth + + def build(self): + mc.setBlocks(self.x, self.y, self.z, + self.x + self.width, self.y + self.height, self.z + self.depth, 4) + + mc.setBlocks(self.x + 1, self.y + 1, self.z + 1, + self.x + self.width - 1, self.y + self.height - 1, self.z + self.depth - 1, 0) + + self.buildWindows() + self.buildDoor() + + def clear(self): + mc.setBlocks(self.x, self.y, self.z, + self.x + self.width, self.y + self.height, self.z + self.depth, 0) + + def buildWindows(self): + mc.setBlock(self.x + (self.width / 4 * 3), self.y + 2, self.z, 0) + mc.setBlock(self.x + (self.width / 4), self.y + 2, self.z, 0) + + def buildDoor(self): + mc.setBlocks(self.x + (self.width / 2), self.y + 1, self.z, self.x + (self.width / 2), self.y + 2, self.z, 0) + + +class Tree(Building): + def build(self): + """Creates a tree at the coordinates given""" + wood = 17 + leaves = 18 + + # trunk + mc.setBlocks(self.x, self.y, self.z, self.x, self.y + 5, self.z, wood) + + # leaves + mc.setBlocks(self.x - 2, self.y + 6, self.z - 2, self.x + 2, self.y + 6, self.z + 2, leaves) + mc.setBlocks(self.x - 1, self.y + 7, self.z - 1, self.x + 1, self.y + 7, self.z + 1, leaves) + + def clear(self): + """Clears a tree at the coordinates given""" + wood = 0 + leaves = 0 + + # trunk + mc.setBlocks(self.x, self.y, self.z, self.x, self.y + 5, self.z, wood) + + # leaves + mc.setBlocks(self.x - 2, self.y + 6, self.z - 2, self.x + 2, self.y + 6, self.z + 2, leaves) + mc.setBlocks(self.x - 1, self.y + 7, self.z - 1, self.x + 1, self.y + 7, self.z + 1, leaves) + +pos = mc.player.getTilePos() +x = pos.x+1 +y = pos.y +z = pos.z+2 + +ghostTree = Tree(x, y, z, 10, 6, 8) +ghostTree.build() + +#time.sleep(10) +print("a tree is created") +#ghostTree.clear() diff --git a/test/BuildRail.py b/test/BuildRail.py index f51ae64..394fa7a 100644 --- a/test/BuildRail.py +++ b/test/BuildRail.py @@ -28,8 +28,8 @@ def BuildRailBridge(mc,p1,p2,clear=False): -serverAddress="192.168.1.155" # change to your minecraft server -playerName ="stoneskin2020" +serverAddress="localhost" # change to your minecraft server +playerName ="stoneskin" pythonApiPort=4712 mc=Minecraft.create(serverAddress,pythonApiPort,playerName) @@ -37,10 +37,10 @@ def BuildRailBridge(mc,p1,p2,clear=False): pos=mc.player.getTilePos() #pos2=Vec3(pos.x,pos.y,pos.z+500) -pos2=Vec3(-789,pos.y,611) +pos2=Vec3(-129,89,-96) BuildRailBridge(mc,Vec3(pos.x+1,pos.y-1,pos.z-1),pos2,False) -BuildPlatform(mc,(pos2.x,pos2.y-1,pos2.z),4,4,1) +#BuildPlatform(mc,(pos2.x,pos2.y-1,pos2.z),4,4,1) #BuildTower(mc,Vec3(pos2.x-1,pos2.y-30,pos2.z),2,2,30,block.WOOD.id,True) diff --git a/test/functions/BuildBridge.py b/test/functions/BuildBridge.py index 1942fc2..ff1d323 100644 --- a/test/functions/BuildBridge.py +++ b/test/functions/BuildBridge.py @@ -6,29 +6,41 @@ def BuildBridge(mc,p1,p2,id,typeId=0,interval=1): print("BuildBridge",p1,p2,id,typeId,interval) step=1 + y=p1.y + intevalY= int(max([abs(p1.x-p2.x),abs(p1.y-p2.y)])/abs(p1.y-p2.y)) if(p1.x>p2.x): step=-1 for x in range(p1.x,p2.x,step): if(id==block.RAIL_POWERED.id): - print(x,p1.y,p1.z) + print(x,y,p1.z) if(x%interval==0): if(id==block.RAIL_POWERED.id and (x==p2.x or x==p1.x )): - mc.setBlock(x,p1.y,p1.z,block.RAIL) + mc.setBlock(x,y,p1.z,block.RAIL) else: - mc.setBlock(x,p1.y,p1.z,id,typeId) + mc.setBlock(x,y,p1.z,id,typeId) #mc.setBlock(x,p1.y,p1.z+1,id) + if(abs(x-p2.x)%intevalY==0): + if((p2.y-y)>0): + y=y+1 + if((p2.y-y)<0): + y=y-1 stepZ=1 if(p1.z>p2.z): stepZ=-1 for z in range(p1.z,p2.z,stepZ): if(id==block.RAIL_POWERED.id): - print(p2.x,p1.y,z) + print(p2.x,y,z) if(z%interval==0): if(id==block.RAIL_POWERED.id and ((z==p2.z) or (z==p1.z) )): - mc.setBlock(p2.x,p1.y,z,block.RAIL) + mc.setBlock(p2.x,y,z,block.RAIL) else: - mc.setBlock(p2.x,p1.y,z,id,typeId) + mc.setBlock(p2.x,y,z,id,typeId) #mc.setBlock(p2.x+1,p1.y,z,id) + if(abs(z-p2.z)%intevalY==0): + if((p2.y-y)>0): + y=y+1 + if((p2.y-y)<0): + y=y-1 def BuildBridge2(mc,p1,p2,id): x=p1.x @@ -52,4 +64,32 @@ def BuildBridge2(mc,p1,p2,id): mc.setBlock(x,y,z,id) mc.setBlock(x+1,y,z,id) print("ct={} ({},{},{})".format(ct,x,y,z)) - ct=ct+1 \ No newline at end of file + ct=ct+1 + +def BuildBridge3(mc,p1,p2,id,typeId=0,interval=1): + x=p1.x + y=p1.y + z=p1.z + + ct=max([abs(p1.x-p2.x),abs(p1.y-p2.y),abs(p1.z-p2.z)]) + stepX=stepY=stepZ=1 + if(p2.x