Apr-18-2019, 11:16 AM
# general function to reset radian angle to [-pi, pi) def reset_radian(radian): while radian >= math.pi: radian = radian - 2*math.pi while radian < -math.pi: radian = radian + 2*math.pi return radian # general function to calculate next position node along a heading direction def cal_next_node(node_poses, index_curr, heading_angle, rep_times): for _ in range(rep_times): index_next = index_curr + 1 x = node_poses[index_curr][0] + 1.0*math.cos(heading_angle) y = node_poses[index_curr][1] + 1.0*math.sin(heading_angle) node_poses[index_next] = np.array([x,y]) index_curr = index_next return index_next ##### script to generate 30-star ##### filename = '30-star' swarm_size = 30 node_poses = np.zeros((swarm_size, 2)) outer_angle = 2*math.pi / 5.0 devia_right = outer_angle devia_left = 2*outer_angle # first node is at bottom left corner heading_angle = outer_angle / 2.0 # current heading heading_dir = 0 # current heading direction: 0 for left, 1 for right seg_count = 0 # current segment count for i in range(1,swarm_size): node_poses[i] = (node_poses[i-1] + np.array([math.cos(heading_angle), math.sin(heading_angle)])) seg_count = seg_count + 1 if seg_count == 3: seg_count = 0 if heading_dir == 0: heading_angle = reset_radian(heading_angle - devia_right) heading_dir = 1 else: heading_angle = reset_radian(heading_angle + devia_left) heading_dir = 0 print(node_poses) with open(filename, 'w') as f: pickle.dump(node_poses, f) pygame.init() # find the right world and screen sizes x_max, y_max = np.max(node_poses, axis=0) x_min, y_min = np.min(node_poses, axis=0) pixel_per_length = 30 world_size = (x_max - x_min + 2.0, y_max - y_min + 2.0) screen_size = (int(world_size[0])*pixel_per_length, int(world_size[1])*pixel_per_length) # convert node poses in the world to disp poses on screen def cal_disp_poses(): poses_temp = np.zeros((swarm_size, 2)) # shift the loop to the middle of the world middle = np.array([(x_max+x_min)/2.0, (y_max+y_min)/2.0]) for i in range(swarm_size): poses_temp[i] = (node_poses[i] - middle + np.array([world_size[0]/2.0, world_size[1]/2.0])) # convert to display coordinates poses_temp[:,0] = poses_temp[:,0] / world_size[0] poses_temp[:,0] = poses_temp[:,0] * screen_size[0] poses_temp[:,1] = poses_temp[:,1] / world_size[1] poses_temp[:,1] = 1.0 - poses_temp[:,1] poses_temp[:,1] = poses_temp[:,1] * screen_size[1] return poses_temp.astype(int) disp_poses = cal_disp_poses() # draw the loop shape on pygame window color_white = (255,255,255) color_black = (0,0,0) screen = pygame.display.set_mode(screen_size) screen.fill(color_white) for i in range(swarm_size): pygame.draw.circle(screen, color_black, disp_poses[i], 5, 0) for i in range(swarm_size-1): pygame.draw.line(screen, color_black, disp_poses[i], disp_poses[i+1], 2) pygame.draw.line(screen, color_black, disp_poses[0], disp_poses[swarm_size-1], 2) pygame.display.update()
Output:[img]https://drive.google.com/open?id=1PjnxxuHCU8SGJcHckP1Oc1QQgEi2GK2U[/img]