diff --git a/functions.py b/functions.py index d6b91c0..79e6f01 100644 --- a/functions.py +++ b/functions.py @@ -174,18 +174,26 @@ # new functions -def generate_cam_matrix(rx_D: int, ry_D: int, rz_D: int, player_pos): - #rx = math.radians(rx_D) - rx = 0 - ry = math.radians(rx_D) - rz = math.radians(rz_D) +def generate_cam_matrix(rx_d: int, ry_d: int, rz_d: int, player_pos): + rx = math.radians(rx_d) + ry = math.radians(ry_d) + rz = math.radians(rz_d) - rotation_matrix = numpy.array( - [[math.cos(ry)*math.cos(rz), math.sin(rx)*math.sin(ry)*math.cos(rz) - math.cos(rx)*math.sin(rz), math.cos(rx)*math.sin(ry)*math.cos(rz) + math.sin(rx)*math.sin(rz), 0], - [math.cos(ry)*math.sin(rz), math.sin(rx)*math.sin(ry)*math.sin(rz) + math.cos(rx)*math.cos(rz), math.cos(rx)*math.sin(ry)*math.sin(rz) - math.sin(rx)*math.sin(rz), 0], - [-math.sin(ry), math.sin(rx)*math.cos(ry), math.cos(rx)*math.cos(ry), 0], - [0, 0, 0, 1]] - ) + x_rot = numpy.array([[1, 0, 0, 0], + [0, math.cos(rx), math.sin(rx), 0], + [0, -math.sin(rx), math.cos(rx), 0], + [0, 0, 0, 1]]) + + y_rot = numpy.array([[math.cos(ry), 0, -math.sin(ry), 0], + [0, 1, 0, 0], + [math.sin(ry), 0, math.cos(ry), 0], + [0, 0, 0, 1]]) + + z_rot = numpy.array([[math.cos(rz), math.sin(rz), 0, 0], + [-math.sin(rz), math.cos(rz), 0, 0], + [0, 0, 1, 0], + [0, 0, 0, 1]]) + rotation_matrix = x_rot.dot(y_rot).dot(z_rot) translation_matrix = numpy.array( [[1, 0, 0, player_pos.x], @@ -193,14 +201,29 @@ [0, 0, 1, player_pos.z], [0, 0, 0, 1]] ) - # todo - # make this thing - # generates a transformation matrix for the current camera - # should only be run once per frame (hopefully a performance improvement?) - # return translation_matrix.dot(rotation_matrix) - # return numpy.matmul(translation_matrix, rotation_matrix) - return numpy.matmul(translation_matrix, rotation_matrix) - # return numpy.multiply(translation_matrix, rotation_matrix) + return rotation_matrix.dot(translation_matrix) + + +def gen_inv_rot_matrix(rx_d, ry_d, rz_d): + rx = math.radians(-rx_d) + ry = math.radians(rx_d) + rz = math.radians(-rz_d - 90) + + x_rot = numpy.array([[1, 0, 0, 0], + [0, math.cos(rx), math.sin(rx), 0], + [0, -math.sin(rx), math.cos(rx), 0], + [0, 0, 0, 1]]) + + y_rot = numpy.array([[math.cos(ry), 0, -math.sin(ry), 0], + [0, 1, 0, 0], + [math.sin(ry), 0, math.cos(ry), 0], + [0, 0, 0, 1]]) + + z_rot = numpy.array([[math.cos(rz), math.sin(rz), 0, 0], + [-math.sin(rz), math.cos(rz), 0, 0], + [0, 0, 1, 0], + [0, 0, 0, 1]]) + return z_rot.dot(y_rot).dot(x_rot) def draw_face(face: Face, cam_matrix: numpy.array, fp_dis): diff --git a/main.py b/main.py index cc4585b..0503e6c 100644 --- a/main.py +++ b/main.py @@ -16,7 +16,7 @@ scrWidth = 3.2 # player information -playerPos: Point3D = Point3D(0, 10, 0) +playerPos: Point3D = Point3D(0, 0, 0) playerSpeed: Point3D = Point3D(0, 0, 0) # todo implement these variables into the code @@ -50,7 +50,7 @@ # create cubes cubes: list[Cube] = [] -for x in [[5, 0, 0]]: #[[-12, 3, 4], [2, 2, 2], [2, 0, 0], [0, 2, 0], [0, 0, 0], [6, -8, 4]]: +for x in [[-12, 3, 4], [2, 2, 2], [2, 0, 0], [0, 2, 0], [0, 0, 0], [6, -8, 4]]: cubes.append(Cube(Point3D(x[0], x[1], x[2]), [Colour([255, 0, 0]) for x in range(6)], True, True)) # todo update or remove @@ -109,8 +109,8 @@ if grabbed: # rotate camera if mouse moves dZ, dX = pygame.mouse.get_rel() - rotX -= dX * sensitivity - rotZ += dZ * sensitivity + rotX += dX * sensitivity + rotZ -= dZ * sensitivity # fix camera within movement bounds rotZ = rotZ % 360 @@ -131,6 +131,7 @@ # generate matrices camMatrix = generate_cam_matrix(rotX, rotY, rotZ, playerPos) + invRotMatrix = gen_inv_rot_matrix(rotX, rotY, rotZ) # __draw cubes__ # calculate 3d and project 3d point locations @@ -164,10 +165,11 @@ # add faces for placeable cube if placing: # generate the position for the new cube ('ray cast' out of camera and do weird things) - newCubePos = Point3D._make([reverse_rotate([[blockDistance, 0, 0]], rotX, rotY, -rotZ + 90)[0]][0]) + # newCubePos = Point3D._make([reverse_rotate([[blockDistance, 0, 0]], rotX, rotY, -rotZ + 90)[0]][0]) + newCubePos = Point3D(blockDistance, 0, 0).apply_matrix(invRotMatrix) # todo change this to a .applymatrix - newCubePos.inv_translate(playerPos) - newCubePos.snap() + newCubePos = newCubePos.inv_translate(playerPos) + newCubePos = newCubePos.snap() # generate cube object with position of newCubePos newCube = Cube(newCubePos, placingColours[currentTexture], True, keys[pygame.K_LCTRL]) @@ -186,8 +188,8 @@ # apply camMatrix to allFaces for face in allFaces: for i, point in enumerate(face.points): - # face.points[i] = point.apply_matrix(camMatrix) - face.points[i] = Point3D._make(rotate(point.translate(playerPos), rotX, rotY, rotZ)) + # apply the camera matrix to the points + face.points[i] = face.points[i].apply_matrix(camMatrix) # fix points behind the camera face.fix_points_behind_camera() @@ -210,7 +212,6 @@ i = 0 for i, face in enumerate(allFaces): _2dPoints = [point.get_2d_point(FPDis).conv_coord(size, scale) for point in face.points] -# _2dPoints = [point.conv_coord(size, scale) for point in _2dPoints] # this seems really illegal try: if True: # face_angle([face.points[0], face.points[1], face.points[2]], FPDis, camDistance) > 90: @@ -251,7 +252,7 @@ magnitude = 0 vectoredDirection = [x * magnitude for x in pressedKeys] - rotatedVector = rotate(vectoredDirection, 0, 0, -rotZ) + rotatedVector = rotate(vectoredDirection, 0, 0, rotZ) playerSpeed = Point3D._make( [(speed + ((acc / frameRate) * kPress)) * (1 - (((acc-1) / maxSpeed)/frameRate)) diff --git a/model.py b/model.py index e718057..68118ff 100644 --- a/model.py +++ b/model.py @@ -76,7 +76,9 @@ return self def translate(self, t_vec): - return Point3D(self.x + t_vec.x, self.y + t_vec.y, self.z + t_vec.z) + return Point3D(self.x + t_vec.x, + self.y + t_vec.y, + self.z + t_vec.z) def inv_translate(self, t_vec): return Point3D(self.x - t_vec.x,