| 
									
										
										
										
											2024-03-03 13:10:14 -08:00
										 |  |  | from collections import defaultdict | 
					
						
							|  |  |  | from typing import Dict, Iterable, Mapping, Tuple, TypedDict | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | from zilliandomizer.logic_components.items import ( | 
					
						
							|  |  |  |     Item as ZzItem, | 
					
						
							|  |  |  |     KEYWORD, | 
					
						
							|  |  |  |     NORMAL, | 
					
						
							|  |  |  |     RESCUE, | 
					
						
							|  |  |  |     item_name_to_id as zz_item_name_to_zz_id, | 
					
						
							|  |  |  |     items as zz_items, | 
					
						
							|  |  |  |     item_name_to_item as zz_item_name_to_zz_item, | 
					
						
							|  |  |  | ) | 
					
						
							|  |  |  | from zilliandomizer.logic_components.regions import RegionData | 
					
						
							|  |  |  | from zilliandomizer.low_resources.item_rooms import item_room_codes | 
					
						
							| 
									
										
										
										
											2022-10-20 10:41:11 -07:00
										 |  |  | from zilliandomizer.options import Chars | 
					
						
							|  |  |  | from zilliandomizer.utils.loc_name_maps import loc_to_id as pretty_loc_name_to_id | 
					
						
							| 
									
										
										
										
											2024-03-03 13:10:14 -08:00
										 |  |  | from zilliandomizer.utils import parse_loc_name, parse_reg_name | 
					
						
							|  |  |  | from zilliandomizer.zri.memory import RescueInfo | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2022-10-20 10:41:11 -07:00
										 |  |  | from .config import base_id as base_id | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | item_name_to_id = { | 
					
						
							|  |  |  |     "Apple": 0 + base_id, | 
					
						
							|  |  |  |     "Champ": 1 + base_id, | 
					
						
							|  |  |  |     "JJ": 2 + base_id, | 
					
						
							|  |  |  |     "Win": 3 + base_id, | 
					
						
							|  |  |  |     "Empty": 4 + base_id, | 
					
						
							|  |  |  |     "ID Card": 5 + base_id, | 
					
						
							|  |  |  |     "Red ID Card": 6 + base_id, | 
					
						
							|  |  |  |     "Floppy Disk": 7 + base_id, | 
					
						
							|  |  |  |     "Bread": 8 + base_id, | 
					
						
							|  |  |  |     "Opa-Opa": 9 + base_id, | 
					
						
							|  |  |  |     "Zillion": 10 + base_id, | 
					
						
							|  |  |  |     "Scope": 11 + base_id, | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | _zz_rescue_0 = zz_item_name_to_zz_item["rescue_0"] | 
					
						
							|  |  |  | _zz_rescue_1 = zz_item_name_to_zz_item["rescue_1"] | 
					
						
							|  |  |  | _zz_empty = zz_item_name_to_zz_item["empty"] | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | def make_id_to_others(start_char: Chars) -> Tuple[ | 
					
						
							|  |  |  |     Dict[int, str], Dict[int, int], Dict[int, ZzItem] | 
					
						
							|  |  |  | ]: | 
					
						
							|  |  |  |     """ returns id_to_name, id_to_zz_id, id_to_zz_item """ | 
					
						
							|  |  |  |     id_to_name: Dict[int, str] = {} | 
					
						
							|  |  |  |     id_to_zz_id: Dict[int, int] = {} | 
					
						
							|  |  |  |     id_to_zz_item: Dict[int, ZzItem] = {} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     if start_char == "JJ": | 
					
						
							|  |  |  |         name_to_zz_item = { | 
					
						
							|  |  |  |             "Apple": _zz_rescue_0, | 
					
						
							|  |  |  |             "Champ": _zz_rescue_1, | 
					
						
							|  |  |  |             "JJ": _zz_empty | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |     elif start_char == "Apple": | 
					
						
							|  |  |  |         name_to_zz_item = { | 
					
						
							|  |  |  |             "Apple": _zz_empty, | 
					
						
							|  |  |  |             "Champ": _zz_rescue_1, | 
					
						
							|  |  |  |             "JJ": _zz_rescue_0 | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |     else:  # Champ | 
					
						
							|  |  |  |         name_to_zz_item = { | 
					
						
							|  |  |  |             "Apple": _zz_rescue_0, | 
					
						
							|  |  |  |             "Champ": _zz_empty, | 
					
						
							|  |  |  |             "JJ": _zz_rescue_1 | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     for name, ap_id in item_name_to_id.items(): | 
					
						
							|  |  |  |         id_to_name[ap_id] = name | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         if ap_id >= 4 + base_id: | 
					
						
							|  |  |  |             index = ap_id - base_id | 
					
						
							|  |  |  |             zz_item = zz_items[index] | 
					
						
							|  |  |  |             assert zz_item.id == index and zz_item.name == name | 
					
						
							|  |  |  |         elif ap_id < 3 + base_id: | 
					
						
							|  |  |  |             # rescue | 
					
						
							|  |  |  |             assert name in {"Apple", "Champ", "JJ"} | 
					
						
							|  |  |  |             zz_item = name_to_zz_item[name] | 
					
						
							|  |  |  |         else:  # main | 
					
						
							|  |  |  |             zz_item = zz_item_name_to_zz_item["main"] | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         id_to_zz_id[ap_id] = zz_item_name_to_zz_id[zz_item.debug_name] | 
					
						
							|  |  |  |         id_to_zz_item[ap_id] = zz_item | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     return id_to_name, id_to_zz_id, id_to_zz_item | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | def make_room_name(row: int, col: int) -> str: | 
					
						
							|  |  |  |     return f"{chr(ord('A') + row - 1)}-{col + 1}" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | loc_name_to_id: Dict[str, int] = { | 
					
						
							|  |  |  |     name: id_ + base_id | 
					
						
							|  |  |  |     for name, id_ in pretty_loc_name_to_id.items() | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | def zz_reg_name_to_reg_name(zz_reg_name: str) -> str: | 
					
						
							|  |  |  |     if zz_reg_name[0] == 'r' and zz_reg_name[3] == 'c': | 
					
						
							|  |  |  |         row, col = parse_reg_name(zz_reg_name) | 
					
						
							|  |  |  |         end = zz_reg_name[5:] | 
					
						
							|  |  |  |         return f"{make_room_name(row, col)} {end.upper()}" | 
					
						
							|  |  |  |     return zz_reg_name | 
					
						
							| 
									
										
										
										
											2024-03-03 13:10:14 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class ClientRescue(TypedDict): | 
					
						
							|  |  |  |     start_char: Chars | 
					
						
							|  |  |  |     room_code: int | 
					
						
							|  |  |  |     mask: int | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class ZillionSlotInfo(TypedDict): | 
					
						
							|  |  |  |     start_char: Chars | 
					
						
							|  |  |  |     rescues: Dict[str, ClientRescue] | 
					
						
							|  |  |  |     loc_mem_to_id: Dict[int, int] | 
					
						
							|  |  |  |     """ memory location of canister to Archipelago location id number """ | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | def get_slot_info(regions: Iterable[RegionData], | 
					
						
							|  |  |  |                   start_char: Chars, | 
					
						
							|  |  |  |                   loc_name_to_pretty: Mapping[str, str]) -> ZillionSlotInfo: | 
					
						
							|  |  |  |     items_placed_in_map_index: Dict[int, int] = defaultdict(int) | 
					
						
							|  |  |  |     rescue_locations: Dict[int, RescueInfo] = {} | 
					
						
							|  |  |  |     loc_memory_to_loc_id: Dict[int, int] = {} | 
					
						
							|  |  |  |     for region in regions: | 
					
						
							|  |  |  |         for loc in region.locations: | 
					
						
							|  |  |  |             assert loc.item, ("There should be an item placed in every location before " | 
					
						
							|  |  |  |                               f"writing slot info. {loc.name} is missing item.") | 
					
						
							|  |  |  |             if loc.item.code in {KEYWORD, NORMAL, RESCUE}: | 
					
						
							|  |  |  |                 row, col, _y, _x = parse_loc_name(loc.name) | 
					
						
							|  |  |  |                 map_index = row * 8 + col | 
					
						
							|  |  |  |                 item_no = items_placed_in_map_index[map_index] | 
					
						
							|  |  |  |                 room_code = item_room_codes[map_index] | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |                 r = room_code | 
					
						
							|  |  |  |                 m = 1 << item_no | 
					
						
							|  |  |  |                 if loc.item.code == RESCUE: | 
					
						
							|  |  |  |                     rescue_locations[loc.item.id] = RescueInfo(start_char, r, m) | 
					
						
							|  |  |  |                 loc_memory = (r << 7) | m | 
					
						
							|  |  |  |                 loc_memory_to_loc_id[loc_memory] = pretty_loc_name_to_id[loc_name_to_pretty[loc.name]] | 
					
						
							|  |  |  |                 items_placed_in_map_index[map_index] += 1 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     rescues: Dict[str, ClientRescue] = {} | 
					
						
							|  |  |  |     for i in (0, 1): | 
					
						
							|  |  |  |         if i in rescue_locations: | 
					
						
							|  |  |  |             ri = rescue_locations[i] | 
					
						
							|  |  |  |             rescues[str(i)] = { | 
					
						
							|  |  |  |                 "start_char": ri.start_char, | 
					
						
							|  |  |  |                 "room_code": ri.room_code, | 
					
						
							|  |  |  |                 "mask": ri.mask | 
					
						
							|  |  |  |             } | 
					
						
							|  |  |  |     return { | 
					
						
							|  |  |  |         "start_char": start_char, | 
					
						
							|  |  |  |         "rescues": rescues, | 
					
						
							|  |  |  |         "loc_mem_to_id": loc_memory_to_loc_id | 
					
						
							|  |  |  |     } |