import json import sys import shutil from kikit.panelize import Origin,getOriginCoord from kikit.common import findBoardBoundingBox from pcbnewTransition.pcbnew import LoadBoard PCB_DIV_MM = 1000000 proj_file = sys.argv[1] pcb_file = sys.argv[2] panel_file = sys.argv[3] def str_mm_to_float(input: str) -> float: input = input.lower() # Panic, should all be in mm for sanity's sake if "mm" not in input: print(input, "not in mm") exit(1) return float(input.replace("mm", "")) def float_to_str_mm(input: float, n: int=0) -> str: return "{:.2f}".format(input).zfill(n+3)+"mm" def float_to_deg(input: float, n: int=0) -> str: return "{:.2f}".format(input).zfill(n+3)+"deg" class Text: def __init__(self, text: str, anchor: str, offset: tuple[float, float], rot: float, size: tuple[float, float, float] = (1.0, 1.0, 0.16), just: tuple[str, str] = ('center', 'center')): self.text = text self.anchor = anchor self.hoff = float_to_str_mm(offset[0]) self.voff = float_to_str_mm(offset[1]) self.rot = str(rot)+"deg" self.width = float_to_str_mm(size[0]) self.height = float_to_str_mm(size[1]) self.thickness = float_to_str_mm(size[2]) self.hjust = just[0] self.vjust = just[1] def to_dict(self, n: int) -> dict: if n == 0: str_n = '' else: str_n = str(n + 1) return { "text" + str_n: { "type": "simple", "text": self.text, "anchor": self.anchor, "hoffset": self.hoff, "voffset": self.voff, "orientation": self.rot, "width": self.width, "height": self.height, "hjustify": self.hjust, "vjustify": self.vjust, "thickness": self.thickness, } } class Frame: def __init__(self, ftype: str, width: str, spacing: str): self.ftype = ftype.lower() self.width = str_mm_to_float(width) self.spacing = str_mm_to_float(spacing) if "frame" in self.ftype: self.extra_d = [(self.width + self.spacing)*2, (self.width + self.spacing)*2] elif "tb" in self.ftype: self.extra_d = [0, (self.width + self.spacing)*2] else: self.extra_d = [(self.width + self.spacing)*2, 0] class Board: def __init__(self, fids: list[tuple[float, float]], rot: float, dims: tuple[float, float]): fid_list = [] for f in fids: fid_list.append("(" + float_to_str_mm(f[0]) + ", " + float_to_str_mm(f[1]) + ")") self.fids = ",".join(fid_list) self.rot = rot self.dims = dims class Panel: def __init__(self, spacing: str, grid: (int, int), frame: Frame, board: Board): self.spacing = str_mm_to_float(spacing) self.grid = grid self.gaps = (grid[0] - 1, grid[1] - 1) self.frame = frame self.text = None self.text2 = None self.text3 = None self.text4 = None self.dims = [self.gaps[i]*self.spacing + self.grid[i]*board.dims[i] + frame.extra_d[i] for i in range(0,2)] arrow_off = [frame.spacing + frame.width, frame.width] text_off = [arrow_off[0] + 2, frame.width/2] if "frame" in frame.ftype or "tb" in frame.ftype: txt_loc = ('mt', 'bl') txt_off = ((0, text_off[1]), (text_off[0], -text_off[1])) txt_just = (('center', 'center'), ('left', 'center')) txt_rot = 0 else: txt_loc = ('ml', 'br') txt_off = ((text_off[1], 0), (text_off[1], text_off[0])) txt_just = (('center', 'center'), ('center', 'center')) txt_rot = 90 self.text = Text("{boardTitle}-{boardRevision}", txt_loc[0], txt_off[0], txt_rot, just=txt_just[0]).to_dict(0) spacer = " " txt =\ "PNL (x,y) : (" + "x: " +float_to_str_mm(self.dims[0],4) + ", " + float_to_str_mm(self.dims[1],4) + ")\n" +\ "BRD (x,y),r: (" + float_to_str_mm(board.dims[0],4) + ", " + float_to_str_mm(board.dims[1],4) + "), " +\ float_to_deg(board.rot, 3) + "\n" +\ "FIDS (x,y) : " + board.fids self.text2 = Text(txt, txt_loc[1], txt_off[1], txt_rot, just=txt_just[1]).to_dict(1) if "frame" in self.frame.ftype: self.text3 = Text("ORIGY ->", "bl", (arrow_off[1], -arrow_off[0]), 0, just=("right", "center")).to_dict(2) self.text4 = Text("ORIGX ->", "bl", (arrow_off[0], -arrow_off[1]), 90, just=("right", "center")).to_dict(3) print("Starting pre_panel script") board = LoadBoard(pcb_file) sourceArea = findBoardBoundingBox(board) # bottomOrig = [(a - b)/10**6 for a,b in zip(*[list(getOriginCoord(o, sourceArea)) for o in [Origin.BottomRight, Origin.BottomLeft]])] # print("bottom Orig: ", bottomOrig) fids = [] for foot in board.Footprints(): if "FID" in foot.GetReference(): cent = foot.GetBoundingBox().GetCenter() fids.append(tuple([cent[i]/PCB_DIV_MM for i in range(0,2)])) print("Fids:", fids) dest_folder = '/'.join(proj_file.split('/')[:-1]) dest_name = proj_file.split('/')[-1].removesuffix(".kicad_pro") src_name = pcb_file.removesuffix(".kicad_pcb") src_proj = src_name + ".kicad_pro" try: shutil.copy(src_name + ".kicad_dru", dest_folder + "/" + dest_name + ".kicad_dru") except Exception: pass json_file = open(panel_file) json_str = json_file.read() panel_json = json.loads(json_str) print(panel_json) frame = Frame(panel_json["framing"]["type"], panel_json["framing"]["width"], panel_json["framing"]["space"]) board = Board(fids, panel_json["layout"].get("rotation", "0deg"), (sourceArea.GetWidth()/PCB_DIV_MM, sourceArea.GetHeight()/PCB_DIV_MM)) panel = Panel(panel_json["layout"]["space"], (int(panel_json["layout"]["rows"]), int(panel_json["layout"]["rows"])) ,frame, board) for t in [panel.text, panel.text2, panel.text3, panel.text4]: if t is not None: panel_json.update(t) # panel_json.update(panel.text3) # json_file = open(src_proj) # json_str = json_file.read() # src = json.loads(json_str) # # json_file = open(proj_file) # json_str = json_file.read() # dest = json.loads(json_str) # json_file = open(panel_file, mode="w") json.dump(panel_json, json_file, indent=4) print("Finished pre_panel script")