def crop_sample(sample): """ Given a sample image with bounding box, this method returns the image crop at the bounding box location with twice the width and height for context. """ output_sample = {} opts = {} image, bb = sample['image'], sample['bb'] orig_bbox = BoundingBox(bb[0], bb[1], bb[2], bb[3]) (output_image, pad_image_location, edge_spacing_x, edge_spacing_y) = cropPadImage(orig_bbox, image) new_bbox = BoundingBox(0, 0, 0, 0) new_bbox = new_bbox.recenter(pad_image_location, edge_spacing_x, edge_spacing_y, new_bbox) output_sample['image'] = output_image output_sample['bb'] = new_bbox.get_bb_list() # additional options for visualization opts['edge_spacing_x'] = edge_spacing_x opts['edge_spacing_y'] = edge_spacing_y opts['search_location'] = pad_image_location opts['search_region'] = output_image return output_sample, opts
def shift_crop_training_sample(sample, bb_params): """ Given an image with bounding box, this method randomly shifts the box and generates a training example. It returns current image crop with shifted box (with respect to current image). """ output_sample = {} opts = {} currimg = sample['image'] currbb = sample['bb'] bbox_curr_gt = BoundingBox(currbb[0], currbb[1], currbb[2], currbb[3]) bbox_curr_shift = BoundingBox(0, 0, 0, 0) bbox_curr_shift = bbox_curr_gt.shift(currimg, bb_params['lambda_scale_frac'], bb_params['lambda_shift_frac'], bb_params['min_scale'], bb_params['max_scale'], True, bbox_curr_shift) (rand_search_region, rand_search_location, edge_spacing_x, edge_spacing_y) = cropPadImage(bbox_curr_shift, currimg) bbox_curr_gt = BoundingBox(currbb[0], currbb[1], currbb[2], currbb[3]) bbox_gt_recentered = BoundingBox(0, 0, 0, 0) bbox_gt_recentered = bbox_curr_gt.recenter(rand_search_location, edge_spacing_x, edge_spacing_y, bbox_gt_recentered) output_sample['image'] = rand_search_region output_sample['bb'] = bbox_gt_recentered.get_bb_list() # additional options for visualization opts['edge_spacing_x'] = edge_spacing_x opts['edge_spacing_y'] = edge_spacing_y opts['search_location'] = rand_search_location opts['search_region'] = rand_search_region return output_sample, opts
def test_iou(self): a = BoundingBox(253, 66, 30, 30) b = BoundingBox(251, 67, 32, 32) iou = a.iou(b) iou2 = b.iou(a) self.assertEqual(iou, iou2) self.assertGreater(iou, 0.8)
def get_sprite_bbox(coord, spritesheet, border_color, border_thickness=1): """ Return the bounding box of the sprite at <coord> in <spritesheet> with <border_color> is spritesheet background color. <border_thickness> is the size of the border surrounding the sprite """ x, y = coord selected_pixel = spritesheet.getpixel((x, y)) if selected_pixel == border_color: return None # get bounding box surrounding selected pixel bbox = BoundingBox(x - 1, y - 1, x + 2, y + 2) sprite = crop(spritesheet, bbox) # since the option can be 0, we need at least 1 pixel thickness to detect border, after that we subtract the result border_thickness += 1 while not have_all_border(sprite, border_color, border_thickness): if bbox.left <= 0 or bbox.top <= 0 or bbox.right > spritesheet.width or bbox.bottom > spritesheet.height: return BoundingBox.empty_bbox() while not have_top_border(sprite, border_color, border_thickness) and bbox.top > 0: bbox.top -= 1 sprite = crop(spritesheet, bbox) while not have_bottom_border( sprite, border_color, border_thickness) and bbox.bottom <= spritesheet.height: bbox.bottom += 1 sprite = crop(spritesheet, bbox) while not have_left_border(sprite, border_color, border_thickness) and bbox.left > 0: bbox.left -= 1 sprite = crop(spritesheet, bbox) while not have_right_border( sprite, border_color, border_thickness) and bbox.right <= spritesheet.width: bbox.right += 1 sprite = crop(spritesheet, bbox) # after have_all_border() return False we have a bounding box that has extra one pixel border bbox = BoundingBox(bbox.left + 1, bbox.top + 1, bbox.right - 1, bbox.bottom - 1) if debugging: print(str(bbox)) # sprite.show() return bbox
def __call__(self, sample, opts): image, bb = sample['image'], sample['bb'] image_x2 = None img_x2 = None if ('image_x2' in sample): image_x2 = sample['image_x2'] h, w = image.shape[:2] if isinstance(self.output_size, int): if h > w: new_h, new_w = self.output_size * h / w, self.output_size else: new_h, new_w = self.output_size, self.output_size * w / h else: new_h, new_w = self.output_size new_h, new_w = int(new_h), int(new_w) # make sure that gray image has 3 channels img = cv2.resize(image, (new_h, new_w), interpolation=cv2.INTER_CUBIC) if image_x2 is not None: img_x2 = cv2.resize(image_x2, (new_h * 2, new_w * 2), interpolation=cv2.INTER_CUBIC) bbox = BoundingBox(bb[0], bb[1], bb[2], bb[3]) bbox.scale(opts['search_region']) return {'image': img, 'image_x2': img_x2, 'bb': bbox.get_bb_list()}
def read_entities(self, entities, entities_removed): self.entity_range = BoundingBox() l = [] for tick, line in entities: xs = line.split() unit = int(xs[0]) id_ = int(xs[1]) + idshift x = int(xs[2]) y = int(xs[3]) direction = int(xs[4]) if not self.attr.is_enemy(id_): self.entity_range.update(x, y) l.append((tick, unit, id_, x, y, direction)) if len(l) > 0: self.maxtick = max(self.maxtick, l[-1][0]) self.entities_created = EventList(l) l = [] for tick, unit in entities_removed: l.append((tick, int(unit))) if len(l) > 0: self.maxtick = max(self.maxtick, l[-1][0]) self.entities_removed = EventList(l)
def computeCropPadImageLocation(bbox_tight, image): # Center of the bounding box bbox_center_x = bbox_tight.get_center_x() bbox_center_y = bbox_tight.get_center_y() image_height = image.shape[0] image_width = image.shape[1] # Padded output width and height output_width = bbox_tight.compute_output_width() output_height = bbox_tight.compute_output_height() roi_left = max(0.0, bbox_center_x - (output_width / 2.)) roi_bottom = max(0.0, bbox_center_y - (output_height / 2.)) # Padded roi width left_half = min(output_width / 2., bbox_center_x) right_half = min(output_width / 2., image_width - bbox_center_x) roi_width = max(1.0, left_half + right_half) # Padded roi height top_half = min(output_height / 2., bbox_center_y) bottom_half = min(output_height / 2., image_height - bbox_center_y) roi_height = max(1.0, top_half + bottom_half) # Padded image location in the original image objPadImageLocation = BoundingBox(roi_left, roi_bottom, roi_left + roi_width, roi_bottom + roi_height) return objPadImageLocation
def overpadsBounds(self, pads=None): bb = BoundingBox() if pads == None: pads = self.pads for pad in pads: pos = pad['pos'] px = pos['x'] py = pos['y'] # Pad outer dimensions sx = pad['size']['x'] sy = pad['size']['y'] angle = pad['pos']['orientation'] # Add each "corner" of the pad (even for oval shapes) p1 = _rotatePoint({'x': -sx / 2, 'y': -sy / 2}, angle) p2 = _rotatePoint({'x': -sx / 2, 'y': +sy / 2}, angle) p3 = _rotatePoint({'x': +sx / 2, 'y': +sy / 2}, angle) p4 = _rotatePoint({'x': +sx / 2, 'y': -sy / 2}, angle) points = [p1, p2, p3, p4] for p in points: x = px + p['x'] y = py + p['y'] bb.addPoint(x, y) return bb
def geometricBoundingBox(self, layer): bb = BoundingBox() # Add all lines lines = self.filterLines(layer) for l in lines: bb.addPoint(l['start']['x'], l['start']['y']) bb.addPoint(l['end']['x'], l['end']['y']) # Add all circles circles=self.filterCircles(layer) for c in circles: cx = c['center']['x'] cy = c['center']['y'] ex = c['end']['x'] ey = c['end']['y'] dx = ex - cx dy = ey - cy r = math.sqrt(dx*dx + dy*dy) bb.addPoint(cx, cy, radius=r) # Add all arcs arcs=self.filterArcs(layer) for c in arcs: cx = c['start']['x'] cy = c['start']['y'] ex = c['end']['x'] ey = c['end']['y'] dx = ex - cx dy = ey - cy r = math.sqrt(dx*dx + dy*dy) dalpha=1 alphaend=c['angle'] if math.fabs(alphaend)<1: dalpha=math.fabs(alphaend)/5 if alphaend<0: dalpha=-dalpha if math.fabs(alphaend)>0: a=0 c0=[ ex - cx, ey - cy ] #print("c0 = ",c0) while (alphaend>0 and a<=alphaend) or (alphaend<0 and a>=alphaend): c1=[0,0] c1[0]=math.cos(a/180*3.1415)*c0[0]-math.sin(a/180*3.1415)*c0[1] c1[1]=math.sin(a/180*3.1415)*c0[0]+math.cos(a/180*3.1415)*c0[1] bb.addPoint(cx + c1[0], cy + c1[1]) a=a+dalpha bb.addPoint(ex, None) return bb
def break_into_chunks(self, bbox, ng_chunk_size, offset, mip, render=False): chunks = [] raw_x_range = bbox.x_range(mip=mip) raw_y_range = bbox.y_range(mip=mip) x_chunk = ng_chunk_size[0] y_chunk = ng_chunk_size[1] x_offset = offset[0] y_offset = offset[1] x_remainder = ((raw_x_range[0] - x_offset) % x_chunk) y_remainder = ((raw_y_range[0] - y_offset) % y_chunk) x_delta = 0 y_delta = 0 if x_remainder != 0: x_delta = x_chunk - x_remainder if y_remainder != 0: y_delta = y_chunk - y_remainder calign_x_range = [raw_x_range[0] - x_remainder, raw_x_range[1]] calign_y_range = [raw_y_range[0] - y_remainder, raw_y_range[1]] x_start = calign_x_range[0] - x_chunk y_start = calign_y_range[0] - y_chunk if (self.process_high_mip > mip): high_mip_scale = 2**(self.process_high_mip - mip) else: high_mip_scale = 1 processing_chunk = (int(self.high_mip_chunk[0] * high_mip_scale), int(self.high_mip_chunk[1] * high_mip_scale)) if not render and (processing_chunk[0] > self.max_chunk[0] or processing_chunk[1] > self.max_chunk[1]): processing_chunk = self.max_chunk elif render and (processing_chunk[0] > self.max_render_chunk[0] or processing_chunk[1] > self.max_render_chunk[1]): processing_chunk = self.max_render_chunk for xs in range(calign_x_range[0], calign_x_range[1], processing_chunk[0]): for ys in range(calign_y_range[0], calign_y_range[1], processing_chunk[1]): chunks.append( BoundingBox(xs, xs + processing_chunk[0], ys, ys + processing_chunk[0], mip=mip, max_mip=self.high_mip)) return chunks
def boundingBox(self): """Return the bounding box of the control polygon. """ bb = BoundingBox() for i, p in enumerate(self.pnts): bb.addPoint(p) bb.addPoint(p + self.intangents[i]) bb.addPoint(p + self.outtangents[i]) return bb
def __init__(self, num_boids, big_boids, dimensions=3, start_center=[1.5, 1.5, 0.5], rule1_factor=0.01, rule2_threshold=0.0005, rule2_factor=1.0, rule3_factor=0.16, bounds_factor=0.01, escape_threshold=0.1, min_velocity2=0.0003, max_velocity2=0.01, rule_direction=0.002, in_random_direction=False, enforce_bounds=True, use_global_velocity_average=False, num_neighbors=10, dt=0.1, use_process=False): super(Boids, self).__init__(num_boids, dimensions, min_velocity2 * dt, max_velocity2 * dt, start_center=start_center, num_neighbors=num_neighbors) self.big_boids = big_boids self.rule1_factor = rule1_factor * dt self.rule2_threshold = rule2_threshold self.rule2_factor = rule2_factor * dt self.rule3_factor = rule3_factor * dt #self.bounds = BoundingBox(min=[-1.0, -0.5, -1.1], max=[1.9, 1.5, 2.1]) self.bounds = BoundingBox(min=[-2.0, 0, -2], max=[2, 2, 2]) self.bounds_factor = bounds_factor * dt self.escapes = np.array([]) self.escape_threshold = escape_threshold self.rule_direction = rule_direction self.direction = np.array(dimensions * [0.5]) self.direction_mask = np.array(self.size * [False]) self.in_random_direction = in_random_direction self.enforce_bounds = enforce_bounds self.tmp_matrix = np.zeros((self.size, self.dimensions)) self.use_process = use_process if self.use_process: self.velocity_worker = worker.WorkerProcess( 'converge velocity', NeighborConverge(self.dimensions, self.size, self.rule3_factor), {'matrix': None}, {'converged': None}) self.position_worker = worker.WorkerProcess( 'converge position', NeighborConverge(self.dimensions, self.size, self.rule1_factor), {'matrix': None}, {'converged': None})
def padsBounds(self, pads=None): bb = BoundingBox() if pads == None: pads = self.pads for pad in pads: pos = pad['pos'] bb.addPoint(pos['x'], pos['y']) return bb
def padsBounds(self, pads: Optional[List[Dict[str, Any]]] = None) -> BoundingBox: bb = BoundingBox() if pads is None: pads = self.pads for pad in pads: pos = pad["pos"] bb.addPoint(pos["x"], pos["y"]) return bb
def read_charts(self, tiles_init): self.charted_range = BoundingBox() l = [] for tick, line in tiles_init: xs = line.split() x = int(xs[0]) y = int(xs[1]) l.append((tick, x, y, xs[2])) self.charted_range.update(32 * x, 32 * y) self.charted_range.update(32 * x + 31, 32 * y + 31) if len(l) > 0: self.maxtick = max(self.maxtick, l[-1][0]) self.charts = EventList(l)
def accumulate_ground_truth_boxes(self, trackid_bbox_dict): """ :param trackid_bbox_dict: Dictionary containing key as track ID, value is a list having bounding box coordinates in the format (xmin, ymin, xmax, ymax) :return: """ # boxes = [] boxes = {} for ech_trkid, bbox_lst in trackid_bbox_dict.items(): x = bbox_lst[0] y = bbox_lst[1] w = bbox_lst[2] - bbox_lst[0] h = bbox_lst[3] - bbox_lst[1] box = BoundingBox(x, y, w, h) # boxes.append(box) boxes[ech_trkid] = box return boxes
def get_rect(self, sample): """ Regresses the bounding box coordinates in the original image dimensions for an input sample. """ x1, x2 = sample['previmg'], sample['currimg'] x1 = x1.unsqueeze(0).to(self.device) x2 = x2.unsqueeze(0).to(self.device) y = self.model(x1, x2) bb = y.data.cpu().numpy().transpose((1, 0)) bb = bb[:, 0] bbox = BoundingBox(bb[0], bb[1], bb[2], bb[3]) # inplace conversion bbox.unscale(self.opts['search_region']) bbox.uncenter(self.curr_img, self.opts['search_location'], self.opts['edge_spacing_x'], self.opts['edge_spacing_y']) return bbox.get_bb_list()
def postprocess(buffer, image_width, image_height, conf_threshold=0.8, nms_threshold=0.5): detected_objects = [] img_scale = [ image_width / INPUT_WIDTH, image_height / INPUT_HEIGHT, image_width / INPUT_WIDTH, image_height / INPUT_HEIGHT ] num_bboxes = int(buffer[0, 0, 0, 0]) if num_bboxes: bboxes = buffer[0, 1:(num_bboxes * 7 + 1), 0, 0].reshape(-1, 7) labels = set(bboxes[:, 5].astype(int)) for label in labels: selected_bboxes = bboxes[np.where((bboxes[:, 5] == label) & ( (bboxes[:, 4] * bboxes[:, 6]) >= conf_threshold))] selected_bboxes_keep = selected_bboxes[nms( selected_bboxes[:, :4], selected_bboxes[:, 4] * selected_bboxes[:, 6], nms_threshold)] for idx in range(selected_bboxes_keep.shape[0]): box_xy = selected_bboxes_keep[idx, :2] box_wh = selected_bboxes_keep[idx, 2:4] score = selected_bboxes_keep[idx, 4] * selected_bboxes_keep[idx, 6] box_x1y1 = box_xy - (box_wh / 2) box_x2y2 = np.minimum(box_xy + (box_wh / 2), [INPUT_WIDTH, INPUT_HEIGHT]) box = np.concatenate([box_x1y1, box_x2y2]) box *= img_scale if box[0] == box[2]: continue if box[1] == box[3]: continue detected_objects.append( BoundingBox(label, score, box[0], box[2], box[1], box[3], image_height, image_width)) return detected_objects
def reset(self, seq_name=None, startFromFirst=False): """ Repeats NO-OP action until a new episode begins. """ self.seq_id = seq_name if seq_name else random.choice(self.seq_names) self.gts = [BoundingBox(*i) for i in self.dataset[self.seq_id]['gt']] self.images = self.dataset[self.seq_id]['images'] self.n_images = len(self.images) assert(self.n_images == len(self.gts)) self.pointer = idx = 1 if startFromFirst else \ 1 + np.random.randint(max(1, self.n_images-self.min_len)) self.stop_idx = idx + self.len_seq img_path = self.data_path + self.seq_id + r'/' + self.images[idx] self.img = Image.open(img_path) ob = crop_resize(self.img, self.gts[idx-1], zoom=self.sample_zoom) self.pos_trackerCurr = self.gts[idx-1] self.cnt_sml_rew = 0 return ob
def get_upchunked_bbox(self, bbox, ng_chunk_size, offset, mip): raw_x_range = bbox.x_range(mip=mip) raw_y_range = bbox.y_range(mip=mip) x_chunk = ng_chunk_size[0] y_chunk = ng_chunk_size[1] x_offset = offset[0] y_offset = offset[1] x_remainder = ((raw_x_range[0] - x_offset) % x_chunk) y_remainder = ((raw_y_range[0] - y_offset) % y_chunk) x_delta = 0 y_delta = 0 if x_remainder != 0: x_delta = x_chunk - x_remainder if y_remainder != 0: y_delta = y_chunk - y_remainder calign_x_range = [raw_x_range[0] + x_delta, raw_x_range[1]] calign_y_range = [raw_y_range[0] + y_delta, raw_y_range[1]] x_start = calign_x_range[0] - x_chunk y_start = calign_y_range[0] - y_chunk x_start_m0 = x_start * 2**mip y_start_m0 = y_start * 2**mip result = BoundingBox(x_start_m0, x_start_m0 + bbox.x_size(mip=0), y_start_m0, y_start_m0 + bbox.y_size(mip=0), mip=0, max_mip=self.process_high_mip) return result
def test_do_action(self): ADNetConf.conf = ADNetConf(None) ADNetConf.conf.conf = { 'action_move': { 'x': 0.03, 'y': 0.03, 'w': 0.03, 'h': 0.03 }, 'predict': { 'stop_iou': 0.93 } } a = BoundingBox(253, 66, 30, 30) b = BoundingBox(251, 67, 32, 32) lb = BoundingBox.get_action_label(b, a) self.assertIn(lb, [4, 5]) # default do_action test a = BoundingBox(252, 65, 25, 30) b = a.do_action(None, 0) c = BoundingBox(251, 65, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 1) c = BoundingBox(250, 65, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 2) c = BoundingBox(253, 65, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 3) c = BoundingBox(254, 65, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 4) c = BoundingBox(252, 64, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 5) c = BoundingBox(252, 63, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 6) c = BoundingBox(252, 66, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 7) c = BoundingBox(252, 67, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 8) c = BoundingBox(252, 65, 25, 30) self.assertEqual(b, c) b = a.do_action(None, 9) c = BoundingBox(253, 66, 23, 28) self.assertEqual(b, c) b = a.do_action(None, 10) c = BoundingBox(251, 64, 27, 32) self.assertEqual(b, c) # box not moved example a = BoundingBox(252, 65, 25, 30) b = a.do_action(None, 2) self.assertNotEqual(a, b)
def _get_bbox(image): bbox = image.getbbox() if bbox is None: return BoundingBox.empty_bbox() return BoundingBox(bbox[0], bbox[1], bbox[2], bbox[3])
def have_border(image, border_color): """ return True if any sides has border """ bbox = _get_main_image_bbox(image, border_color) return bbox != BoundingBox(0, 0, image.size[0], image.size[1])
def geometricBoundingBox(self, layer: str) -> BoundingBox: bb = BoundingBox() # Add all lines lines = self.filterLines(layer) for line in lines: bb.addPoint(line["start"]["x"], line["start"]["y"]) bb.addPoint(line["end"]["x"], line["end"]["y"]) # Add all rects rects = self.filterRects(layer) for r in rects: bb.addPoint(r["start"]["x"], r["start"]["y"]) bb.addPoint(r["end"]["x"], r["end"]["y"]) # Add all circles circles = self.filterCircles(layer) for c in circles: cx = c["center"]["x"] cy = c["center"]["y"] ex = c["end"]["x"] ey = c["end"]["y"] dx = ex - cx dy = ey - cy r = math.sqrt(dx * dx + dy * dy) bb.addPoint(cx, cy, radius=r) polys = self.filterPolys(layer) for p in polys: for pt in p["points"]: bb.addPoint(pt["x"], pt["y"]) # Add all arcs arcs = self.filterArcs(layer) for c in arcs: cx = c["start"]["x"] cy = c["start"]["y"] ex = c["end"]["x"] ey = c["end"]["y"] dx = ex - cx dy = ey - cy r = math.sqrt(dx * dx + dy * dy) dalpha = 1 alphaend = c["angle"] if math.fabs(alphaend) < 1: dalpha = math.fabs(alphaend) / 5 if alphaend < 0: dalpha = -dalpha if math.fabs(alphaend) > 0: a = 0 c0 = [ex - cx, ey - cy] # print("c0 = ",c0) while (alphaend > 0 and a <= alphaend) or (alphaend < 0 and a >= alphaend): c1 = [0, 0] c1[0] = (math.cos(a / 180 * 3.1415) * c0[0] - math.sin(a / 180 * 3.1415) * c0[1]) c1[1] = (math.sin(a / 180 * 3.1415) * c0[0] + math.cos(a / 180 * 3.1415) * c0[1]) bb.addPoint(cx + c1[0], cy + c1[1]) a = a + dalpha bb.addPoint(ex, None) return bb
def __init__(self, settings, vertical_fov=50, bounding_box=BoundingBox([-2.0, 0, -2], [2, 2, 2]), camAzimuth=40.0, camDistance=6.0, camRotZ=45.0): self.settings = settings self.vertical_fov = vertical_fov self.world = bounding_box self.screen_width = settings.screen_width self.screen_height = settings.screen_height self.screen_aspect = float(self.screen_width) / self.screen_height self.background_color = settings.background_color self.show_velocity_vectors = False self.text_pos_x = 0.05 self.text_pos_y = 0.95 self.topview_size = compute_fraction_if_not_absolute( settings.topview_size, self.screen_width) self.topview_left = compute_fraction_if_not_absolute( settings.topview_left, self.screen_width) self.topview_top = compute_fraction_if_not_absolute( settings.topview_top, self.screen_height) self.sideview_size = compute_fraction_if_not_absolute( settings.sideview_size, self.screen_width) self.sideview_left = compute_fraction_if_not_absolute( settings.sideview_left, self.screen_width) self.sideview_top = compute_fraction_if_not_absolute( settings.sideview_top, self.screen_height) self.camDistance = camDistance self.camRotZ = camRotZ self.camAzimuth = camAzimuth self.boids_historic_values = HistoricValues( settings.plot_history_length) self.shadow_boids_historic_values = HistoricValues( settings.plot_history_length) self.historic_boid_positions = [] self.historic_shadow_boid_positions = [] self.show_boids_as_birds = True self.show_world_boundary = False self.boid_scale_factor = settings.boid_scale_factor self.stats_left = compute_fraction_if_not_absolute( settings.stats_left, self.screen_width) self.stats_top = compute_fraction_if_not_absolute( settings.stats_top, self.screen_height) self.stats_width = compute_fraction_if_not_absolute( settings.stats_width, self.screen_width) self.stats_height = compute_fraction_if_not_absolute( settings.stats_height, self.screen_height) self.stats_separation = compute_fraction_if_not_absolute( settings.stats_separation, self.screen_width) self.stats_text_drawer = TextDrawer2(*settings.stats_font) # # Set up plots # self.plot_left = compute_fraction_if_not_absolute( settings.plot_left, self.screen_width) self.plot_top = compute_fraction_if_not_absolute( settings.plot_top, self.screen_height) self.plot_separation = compute_fraction_if_not_absolute( settings.plot_separation, self.screen_height) self.plot_width = compute_fraction_if_not_absolute( settings.plot_width, self.screen_width) self.plot_height = compute_fraction_if_not_absolute( settings.plot_height, self.screen_height) top = self.plot_top POS_ENTROPY_HEIGHT_FACTOR = 2.3 ENTROPY_DIFF_HEIGHT_FACTOR = 1.4 # Bbox diagonal #vp = (self.plot_left, top - self.plot_height, self.plot_width, self.plot_height) #self.bbox_diagonal_plot = Plot('Bounding-box diagonal', vp, (self.boids_historic_values.max_length, 5.0), settings.plot_font) # top -= self.plot_height # top -= self.plot_separation # Position entropy H = int(self.plot_height * POS_ENTROPY_HEIGHT_FACTOR) vp = (self.plot_left, top - H, self.plot_width, H) self.pos_entropy_plot = Plot( 'Entropy (position)', vp, (self.boids_historic_values.max_length, 4.0), settings.plot_font) top -= H top -= self.plot_separation # Number of components #vp = (self.plot_left, top - self.plot_height/2, self.plot_width, self.plot_height/2) #self.num_components_plot = Plot('Number of components', vp, (self.boids_historic_values.max_length, 5.0), settings.plot_font) # top -= self.plot_height / 2 # top -= self.plot_separation # Entropy difference H = int(self.plot_height * ENTROPY_DIFF_HEIGHT_FACTOR) vp = (self.plot_left, top - H, self.plot_width, H) self.pos_entropy_difference_plot = Plot( 'Entropy difference (absolute)', vp, (self.boids_historic_values.max_length, 4.0), settings.plot_font) top -= H top -= self.plot_separation # # Boids stuff # self.boid_redness = None self.boid_model = OBJModel('bird.obj') # # Logos # self.logos = [] for fname in settings.logos: img = StaticImage(fname) self.logos.append(img) h = compute_fraction_if_not_absolute(settings.logo_target_height, self.screen_height) img.scale = 1.0 * h / img.height self.logo_left = compute_fraction_if_not_absolute( settings.logo_left, self.screen_width) self.logo_top = compute_fraction_if_not_absolute( settings.logo_top, self.screen_height) self.logo_separation = compute_fraction_if_not_absolute( settings.logo_separation, self.screen_width) # # Other images # self.rules_image = StaticImage('./images/boid_rules.png') self.rules_left = compute_fraction_if_not_absolute( settings.rules_left, self.screen_width) self.rules_top = compute_fraction_if_not_absolute( settings.rules_top, self.screen_height) self.rules_width = compute_fraction_if_not_absolute( settings.rules_width, self.screen_width) self.rules_image.width = self.rules_width self.rules_image.height = self.rules_width / self.rules_image.aspect self.equation_image = StaticImage('./images/entropy.png') self.equation_left = compute_fraction_if_not_absolute( settings.equation_left, self.screen_width) self.equation_top = compute_fraction_if_not_absolute( settings.equation_top, self.screen_height) self.equation_width = compute_fraction_if_not_absolute( settings.equation_width, self.screen_width) self.equation_image.width = self.equation_width self.equation_image.height = self.equation_width / self.equation_image.aspect # Initialize OpenGL glEnable(GL_DEPTH_TEST) glEnable(GL_POINT_SMOOTH) glEnable(GL_LINE_SMOOTH) glEnableClientState(GL_VERTEX_ARRAY)
def overpadsBounds(self, pads: Optional[List[Dict[str, Any]]] = None) -> BoundingBox: bb = BoundingBox() if pads is None: pads = self.pads for pad in pads: pos = pad["pos"] px = pos["x"] py = pos["y"] # Pad outer dimensions sx = pad["size"]["x"] sy = pad["size"]["y"] angle = -pad["pos"]["orientation"] # Add each "corner" of the pad (even for oval shapes) p1 = _rotatePoint({"x": -sx / 2, "y": -sy / 2}, angle) p2 = _rotatePoint({"x": -sx / 2, "y": +sy / 2}, angle) p3 = _rotatePoint({"x": +sx / 2, "y": +sy / 2}, angle) p4 = _rotatePoint({"x": +sx / 2, "y": -sy / 2}, angle) points = [p1, p2, p3, p4] # Add more points for custom pad shapes if pad["shape"] == "custom": for p in pad["primitives"]: if p["type"] == "gr_poly": # Add polygon points for point in p["pts"]: points.append(_rotatePoint(point, angle)) elif p["type"] == "gr_line": # Add line points s = _rotatePoint(p["start"], angle) e = _rotatePoint(p["end"], angle) w = p["width"] points.append(_movePoint(s, { "x": -w / 2, "y": -w / 2 })) points.append(_movePoint(s, { "x": -w / 2, "y": +w / 2 })) points.append(_movePoint(s, { "x": +w / 2, "y": +w / 2 })) points.append(_movePoint(s, { "x": +w / 2, "y": -w / 2 })) points.append(_movePoint(e, { "x": -w / 2, "y": -w / 2 })) points.append(_movePoint(e, { "x": -w / 2, "y": +w / 2 })) points.append(_movePoint(e, { "x": +w / 2, "y": +w / 2 })) points.append(_movePoint(e, { "x": +w / 2, "y": -w / 2 })) elif p["type"] == "gr_arc": # Add arc points # TODO pass elif p["type"] == "gr_circle": # Add circle points c = _rotatePoint(p["center"], angle) e = _rotatePoint(p["end"], angle) r = math.sqrt((e["x"] - c["x"])**2 + (e["y"] - c["y"])**2) w = p["width"] points.append(_movePoint(c, {"x": -r - w / 2, "y": 0})) points.append(_movePoint(c, {"x": +r + w / 2, "y": 0})) points.append(_movePoint(c, {"x": 0, "y": -r - w / 2})) points.append(_movePoint(c, {"x": 0, "y": +r + w / 2})) for p in points: x = px + p["x"] y = py + p["y"] bb.addPoint(x, y) return bb
def boundingBox(self): return BoundingBox()
def overpadsBounds(self, pads=None): bb = BoundingBox() if pads == None: pads = self.pads for pad in pads: pos = pad['pos'] px = pos['x'] py = pos['y'] # Pad outer dimensions sx = pad['size']['x'] sy = pad['size']['y'] angle = -pad['pos']['orientation'] # Add each "corner" of the pad (even for oval shapes) p1 = _rotatePoint({'x': -sx / 2, 'y': -sy / 2}, angle) p2 = _rotatePoint({'x': -sx / 2, 'y': +sy / 2}, angle) p3 = _rotatePoint({'x': +sx / 2, 'y': +sy / 2}, angle) p4 = _rotatePoint({'x': +sx / 2, 'y': -sy / 2}, angle) points = [p1, p2, p3, p4] # Add more points for custom pad shapes if pad['shape'] == 'custom': for p in pad['primitives']: if p['type'] == 'gr_poly': # Add polygon points for point in p['pts']: points.append(_rotatePoint(point, angle)) elif p['type'] == 'gr_line': # Add line points s = _rotatePoint(p['start'], angle) e = _rotatePoint(p['end'], angle) w = p['width'] points.append(_movePoint(s, { 'x': -w / 2, 'y': -w / 2 })) points.append(_movePoint(s, { 'x': -w / 2, 'y': +w / 2 })) points.append(_movePoint(s, { 'x': +w / 2, 'y': +w / 2 })) points.append(_movePoint(s, { 'x': +w / 2, 'y': -w / 2 })) points.append(_movePoint(e, { 'x': -w / 2, 'y': -w / 2 })) points.append(_movePoint(e, { 'x': -w / 2, 'y': +w / 2 })) points.append(_movePoint(e, { 'x': +w / 2, 'y': +w / 2 })) points.append(_movePoint(e, { 'x': +w / 2, 'y': -w / 2 })) elif p['type'] == 'gr_arc': # Add arc points # TODO pass elif p['type'] == 'gr_circle': # Add circle points c = _rotatePoint(p['center'], angle) e = _rotatePoint(p['end'], angle) r = math.sqrt((e['x'] - c['x'])**2 + (e['y'] - c['y'])**2) w = p['width'] points.append(_movePoint(c, {'x': -r - w / 2, 'y': 0})) points.append(_movePoint(c, {'x': +r + w / 2, 'y': 0})) points.append(_movePoint(c, {'x': 0, 'y': -r - w / 2})) points.append(_movePoint(c, {'x': 0, 'y': +r + w / 2})) for p in points: x = px + p['x'] y = py + p['y'] bb.addPoint(x, y) return bb
def bounding_box(self): if self._bounding_box is None: self._bounding_box = BoundingBox(points=self.position) return self._bounding_box
def find_region(p, bb, subdivisions): numRows = int(math.sqrt(subdivisions)) deltax = (bb.upperx - bb.lowerx) / numRows deltay = (bb.uppery - bb.lowery) / numRows res = 1 currx = bb.lowerx curry = bb.lowery while (currx + deltax < p.x): res += 1 currx += deltax while (curry + deltay < p.y): res += 3 curry += deltay return res minx = 1.0 miny = 1.0 maxx = 4.0 maxy = 10.0 x = 3 y = 4 subdivisions = 9 p = Point(x,y) bb = BoundingBox(minx, miny, maxx, maxy) print(find_region(p, bb, subdivisions)) print(bb.find_region(p, subdivisions)) realPoints = [[-122.31192812169945, 47.6614570810238], [-122.31193521966424, 47.66115340231431], [-122.31193522443823, 47.66070126235127], [-122.31193492573357, 47.66014380783554], [-122.31194969832706, 47.659755560834014], [-122.31195494321685, 47.659044323884814], [-122.3141761, 47.66120963], [-122.31343051, 47.66129026], [-122.31276334, 47.66129834], [-122.31194188, 47.66115757], [-122.31196199, 47.66105298], [-122.31195995, 47.66074168], [-122.31195979, 47.65956427], [-122.31198085, 47.65914122]]