├── README.md ├── assets ├── CHIP.pyxres └── CHIP.pyxpal └── viewer.py /README.md: -------------------------------------------------------------------------------- 1 | ### Prerequisites 2 | - pyxel 3 | -------------------------------------------------------------------------------- /assets/CHIP.pyxres: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/kadomoto/viewer/main/assets/CHIP.pyxres -------------------------------------------------------------------------------- /assets/CHIP.pyxpal: -------------------------------------------------------------------------------- 1 | 000000 2 | 2B335F 3 | 7E2072 4 | 19959C 5 | 8B4B52 6 | 395C98 7 | A9C1FF 8 | EEEEEE 9 | D4186C 10 | D38441 11 | E9C35B 12 | 70C6A9 13 | 7696DE 14 | E3E3E3 15 | FF9798 16 | EDC7B0 -------------------------------------------------------------------------------- /viewer.py: -------------------------------------------------------------------------------- 1 | import pyxel 2 | 3 | import json 4 | import argparse 5 | import random 6 | 7 | DISPLAY_AREA = 320 8 | CHIP_AREA = 256 # chip area 9 | SIZE = 6 # chip size 10 | CENTER = CHIP_AREA // SIZE * SIZE / 2 11 | 12 | COORD_NUM = 1 13 | ROUT_NUM = 0 14 | 15 | 16 | class Vec2: 17 | def __init__(self, x, y): 18 | self.x = x 19 | self.y = y 20 | 21 | 22 | class Chip: 23 | def __init__(self, x, y): 24 | self.pos = Vec2(x, y) 25 | 26 | 27 | class App: 28 | def __init__(self, json_path): 29 | pyxel.init(DISPLAY_AREA, DISPLAY_AREA, title="viewer", quit_key=pyxel.KEY_Q) 30 | pyxel.load("assets/CHIP.pyxres") 31 | pyxel.mouse(True) 32 | # sound effect 33 | pyxel.sound(0).set("a3a2c1a1", "t", "7", "s", 5) 34 | pyxel.sound(1).set("a3e2a1", "p", "7", "s", 5) 35 | 36 | if json_path is None: 37 | print("no json file") 38 | chip_data = None 39 | # chip list 40 | self.chips = [] 41 | # coordinator 42 | new_coord = Chip(CENTER, CENTER) 43 | self.chips.append(new_coord) 44 | else: 45 | print("Read json file") 46 | with open(json_path, 'r') as f: 47 | chip_data = json.load(f) 48 | print(chip_data) 49 | # chip list 50 | self.chips = [] # [Chip()] 51 | self.chipDict = {} # {'node_id': (x, y)} 52 | self.chipPositions = {} # {(x, y): 'node_id'} 53 | 54 | # coordinator 55 | new_coord = Chip(CENTER, CENTER) 56 | self.chips.append(new_coord) 57 | self.chipDict.update([('0', (0, 0))]) 58 | self.chipPositions.update([((0, 0), '0')]) 59 | 60 | # routers 61 | for node in chip_data['adjacencies'].items(): 62 | dict, pos = self.nodePos(node) 63 | self.chipDict.update(dict) 64 | self.chipPositions.update(pos) 65 | 66 | for position in self.chipPositions: 67 | if (position[0] == 0 and position[1] == 0): 68 | pass 69 | else: 70 | new_rout = Chip(CENTER + position[0]*SIZE, CENTER + position[1]*SIZE) 71 | self.chips.append(new_rout) 72 | 73 | pyxel.run(self.update, self.draw) 74 | 75 | def nodePos(self, node): 76 | adjacent_node_num = len(node[1]) 77 | for adjacent_node in node[1]: 78 | if adjacent_node in self.chipDict: adjacent_node_num = adjacent_node_num - 1 79 | random_positions = self.randomPos(self.chipDict[node[0]], adjacent_node_num) 80 | node_list = [] 81 | position_list = [] 82 | i = 0 83 | for adjacent_node in node[1]: 84 | if adjacent_node in self.chipDict: 85 | pass 86 | else: 87 | node_list.append((adjacent_node, tuple(random_positions[i]))) 88 | position_list.append((tuple(random_positions[i]), adjacent_node)) 89 | i = i + 1 90 | 91 | return node_list, position_list # list of ('node_id', (x, y)), list of ((x, y), 'node_id') 92 | 93 | def randomPos(self, position, num): 94 | x = position[0] 95 | y = position[1] 96 | pos = [] 97 | if (x+1, y) not in self.chipPositions: pos.append([x+1, y]) 98 | if (x, y-1) not in self.chipPositions: pos.append([x, y-1]) 99 | if (x-1, y) not in self.chipPositions: pos.append([x-1, y]) 100 | if (x, y+1) not in self.chipPositions: pos.append([x, y+1]) 101 | 102 | return random.sample(pos, num) 103 | 104 | def jsonGen(self): 105 | outputDic = {} 106 | num = len(self.chips) 107 | outputDic.update([("num", num)]) 108 | nodes = {} 109 | i = 1 110 | for chip in self.chips: 111 | if (chip.pos.x == CENTER and chip.pos.y == CENTER): 112 | nodes.update([("0", "Coordinator")]) 113 | else: 114 | nodes.update([(str(i), "Router")]) 115 | i = i + 1 116 | outputDic.update([("nodes", nodes)]) 117 | adjacencies = {} 118 | for i, chip_a in enumerate(self.chips): 119 | adjacency = [] 120 | for j, chip_b in enumerate(self.chips): 121 | if ((chip_a.pos.x == chip_b.pos.x - SIZE and chip_a.pos.y == chip_b.pos.y) or 122 | (chip_a.pos.x == chip_b.pos.x and chip_a.pos.y == chip_b.pos.y - SIZE) or 123 | (chip_a.pos.x == chip_b.pos.x + SIZE and chip_a.pos.y == chip_b.pos.y) or 124 | (chip_a.pos.x == chip_b.pos.x and chip_a.pos.y == chip_b.pos.y + SIZE)): 125 | adjacency.append(str(j)) 126 | adjacencies.update([(str(i), adjacency)]) 127 | outputDic.update([("adjacencies", adjacencies)]) 128 | cycles = 10 129 | outputDic.update([("cycles", cycles)]) 130 | with open("output.json", "w") as f: 131 | json.dump(outputDic, f, indent=4) 132 | 133 | def update(self): 134 | if pyxel.btnp(pyxel.MOUSE_BUTTON_LEFT): 135 | if (pyxel.mouse_x < 256 and pyxel.mouse_y < 256): 136 | # router 137 | new_chip = Chip(pyxel.mouse_x // SIZE * SIZE, pyxel.mouse_y // SIZE * SIZE) 138 | # search 139 | #for chip in self.chips: 140 | #if (chip.x == new_chip.x and chip.y == new_chip.y): 141 | #pass 142 | #else: 143 | #self.chips.append(new_chip) 144 | self.chips.append(new_chip) 145 | pyxel.play(0, 0) 146 | elif (15 < pyxel.mouse_x < 71 and 295 < pyxel.mouse_y < 311): 147 | self.jsonGen() 148 | pyxel.play(0, 1) 149 | else: 150 | pass 151 | 152 | def draw(self): 153 | # init 154 | pyxel.cls(7) 155 | for i in range(0, CHIP_AREA, SIZE*2): 156 | for j in range(0, CHIP_AREA, 12): 157 | pyxel.rect(i, j, SIZE, SIZE, 13) 158 | for i in range(SIZE, CHIP_AREA, SIZE*2): 159 | for j in range(SIZE, CHIP_AREA, SIZE*2): 160 | pyxel.rect(i, j, SIZE, SIZE, 13) 161 | 162 | pyxel.rect(15, 295, 56, 16, 5) 163 | pyxel.text(20, 300, "output json", 13) 164 | 165 | for chip in self.chips: 166 | # place a chip 167 | # blt(x, y, img, u, v, w, h, [colkey]) 168 | if (chip.pos.x == CENTER and chip.pos.y == CENTER): 169 | pyxel.blt(chip.pos.x, chip.pos.y, 1, 5, 5, SIZE, SIZE) 170 | else: 171 | pyxel.blt(chip.pos.x, chip.pos.y, 0, 5, 5, SIZE, SIZE) 172 | 173 | 174 | def main(json_path): 175 | App(json_path) 176 | 177 | 178 | if __name__ == "__main__": 179 | parser = argparse.ArgumentParser() 180 | parser.add_argument('--path', type=str, default=None, help='json file path') 181 | args = parser.parse_args() 182 | 183 | main(args.path) 184 | --------------------------------------------------------------------------------