Skip to content

Commit

Permalink
fixed uppercase folder issue
Browse files Browse the repository at this point in the history
  • Loading branch information
Ehseezed authored Oct 29, 2023
1 parent 8aa77d0 commit e274a53
Show file tree
Hide file tree
Showing 15 changed files with 861 additions and 0 deletions.
52 changes: 52 additions & 0 deletions worlds/am2r/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
from typing import Dict
from .items import item_table
from .locations import get_location_datas, EventId
from .regions import create_regions_and_locations
from BaseClasses import Tutorial, Item
from .options import AM2R_options
from worlds.AutoWorld import World, WebWorld


class AM2RWeb(WebWorld):
theme = "partyTime"
tutorials = [Tutorial(
"Multiworld Setup Guide",
"A guide to setting up the Archipelago AM2R software on your computer. This guide covers single-player, multiworld, and related software.",
"English",
"setup_en.md",
"setup/en",
["Zed"]
)]


class AM2RWorld(World):
"""
AM2R is a remake of the classic Metroid 2 game for the Game Boy that tries its best to keep the feel
of the original as well as filling in some gaps to more closely tie into Metroid Fusion and brings some
items from there as well.
"""
game = "AM2R"
option_definitions = options.AM2R_options
web = AM2RWeb()

item_name_to_id = items.item_name_to_id
location_name_to_id = {location.name: location.code for location in get_location_datas(None, None)}

item_name_groups = items.item_name_groups
data_version = 0

def fill_slot_data(self) -> Dict[str, object]:
return {name: getattr(self.multiworld, name)[self.player].value for name in self.option_definitions}

def create_regions(self) -> None:
create_regions_and_locations(self.multiworld, self.player)

def create_item(self, name: str) -> Item:
return items.create_item(self.player, name)

def create_items(self) -> None:
self.multiworld.get_location("The Last Metroid is in Captivity", self.player).place_locked_item(self.create_item("The Galaxy is at Peace"))
items.create_all_items(self.multiworld, self.player)

def set_rules(self) -> None:
self.multiworld.completion_condition[self.player] = lambda state: state.has("The Galaxy is at Peace", self.player)
Binary file added worlds/am2r/__pycache__/__init__.cpython-310.pyc
Binary file not shown.
Binary file added worlds/am2r/__pycache__/items.cpython-310.pyc
Binary file not shown.
Binary file added worlds/am2r/__pycache__/locations.cpython-310.pyc
Binary file not shown.
Binary file added worlds/am2r/__pycache__/options.cpython-310.pyc
Binary file not shown.
Binary file added worlds/am2r/__pycache__/regions.cpython-310.pyc
Binary file not shown.
Binary file added worlds/am2r/__pycache__/rules.cpython-310.pyc
Binary file not shown.
20 changes: 20 additions & 0 deletions worlds/am2r/docs/en_AM2R.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# AM2R Multiworld Beta (Text Adventure)
## How to use
There currently is no client to use this with


Download and install the latest version of [Archipelago](https://github.com/ArchipelagoMW/Archipelago/releases) the `AM2R.apworld` from below.
Once you have installed Archipelago you can take the `AM2R.apworld` and put it inside the `/lib/worlds` portion of your Archipelago install.
From there to get a generic `AM2R.yaml` open the Archipelago Launcher and click the **Generate Template settings** which will add it to the template yaml folder in `/Players/Templates`.
### Things are subject to change at developer discretion
### Seeds should be beatable but its possible there are still logical errors
## Bug Reporting
If you are playing this mod and are encountering bugs **DO NOT** report them to the Archipelago server this is not offical support from them, and they may or may not know what to do instead you can report them to the dedicated mod thread on the [AM2R Server](https://discord.gg/YTQnkAJ) or on the [Modding Server](https://discord.gg/Fdq3MSXEDb) and you can always open an issue on the github.
### Help I found a problem with 100% trap fill playing on fusion mode
Fuck you Abyss said it was possible, and I was there.

## Randomizer Information
### What is randomized?
All items both majors and minors are randomized together in one pool with the option to add in the metroids as checks as well.
### What is the goal?
The goal of this AM2R randomizer implementation is to collect kill or collect the self specified number of metroids to reach the deep caves and then a few more to get into the lab and fight the queen metroid.
12 changes: 12 additions & 0 deletions worlds/am2r/docs/setup_en.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# AM2R Archipelago Setup Guide

## Required Software
[comment]: <> (Change this reference before release)
- [AM2R Multiworld Mod](https://github.com/Ehseezed/Amalgam)
- [AM2R Launcher](https://github.com/AM2R-Community-Developers/AM2RLauncher/releases)
- Your copy of AM2R 1.1 for the launcher

## Installation Process

Download the latest release of [AM2R Launcher](https://github.com/AM2R-Community-Developers/AM2RLauncher/releases) and
then using your AM2R 1.1 set up the launcher once the launcher is set up you can install the mod
144 changes: 144 additions & 0 deletions worlds/am2r/items.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,144 @@
import itertools
from collections import Counter
from typing import Dict, List, NamedTuple, Set

from BaseClasses import Item, ItemClassification, MultiWorld
from .options import MetroidsAreChecks, MetroidsRequired, get_option_value


class ItemData(NamedTuple):
code: int
group: str
classification: ItemClassification = ItemClassification.progression
required_num: int = 0


class AM2RItem(Item):
game: str = "AM2R"


def create_item(player: int, name: str) -> Item:
item_data = item_table[name]
return AM2RItem(name, item_data.classification, item_data.code, player)


def create_fixed_item_pool() -> List[str]:
required_items: Dict[str, int] = {name: data.required_num for name, data in item_table.items()}
return list(Counter(required_items).elements())


def create_metroid_items(MetroidsRequired: MetroidsRequired, MetroidsAreChecks: MetroidsAreChecks) -> List[str]:
metroid_count = 0
if MetroidsAreChecks == MetroidsAreChecks.option_include_A6:
metroid_count = MetroidsRequired.value + 5
elif MetroidsAreChecks == MetroidsAreChecks.option_exclude_A6:
metroid_count += MetroidsRequired.value
return ["Metroid" for _ in range(metroid_count)]


def create_trap_items(multiworld: MultiWorld, player: int, locations_to_trap: int) -> List[str]:
trap_pool = trap_weights.copy()

return multiworld.random.choices(
population=list(trap_pool.keys()),
weights=list(trap_pool.values()),
k=locations_to_trap
)


def create_random_items(multiworld: MultiWorld, player: int, random_count: int) -> List[str]:
filler_pool = filler_weights.copy()

return multiworld.random.choices(
population=list(filler_pool.keys()),
weights=list(filler_pool.values()),
k=random_count
)


def create_all_items(multiworld: MultiWorld, player: int) -> None:
sum_locations = len(multiworld.get_unfilled_locations(player))

itempool = (
create_fixed_item_pool()
+ create_metroid_items(multiworld.MetroidsRequired[player], multiworld.MetroidsAreChecks[player])
)

trap_percentage = get_option_value(multiworld, player, "TrapFillPercentage")
trap_fill = trap_percentage / 100

random_count = sum_locations - len(itempool)
locations_to_trap = int(trap_fill * random_count)
itempool += create_trap_items(multiworld, player, locations_to_trap)

random_count = sum_locations - len(itempool)
itempool += create_random_items(multiworld, player, random_count)

multiworld.itempool += [create_item(player, name) for name in itempool]


item_table: Dict[str, ItemData] = {
"Missile": ItemData(8678000, "Ammo", ItemClassification.filler),
"Super Missile": ItemData(8678001, "Ammo", ItemClassification.progression, 1),
"Power Bomb": ItemData(8678002, "Ammo", ItemClassification.progression, 2),
"Energy Tank": ItemData(8678003, "Ammo", ItemClassification.filler, 1),
# "Arm Cannon": ItemData8678004, ("Equipment", ItemClassification.progression, 1),
# "Morph Ball": ItemData8678005, ("Equipment", ItemClassification.progression, 1),
# "Power Grip": ItemData8678006, ("Equipment", ItemClassification.progression, 1),
"Bombs": ItemData(8678007, "Equipment", ItemClassification.progression, 1),
"Spider Ball": ItemData(8678008, "Equipment", ItemClassification.progression, 1),
"Hi Jump": ItemData(8678009, "Equipment", ItemClassification.progression, 1),
"Spring Ball": ItemData(8678010, "Equipment", ItemClassification.progression, 1),
"Space Jump": ItemData(8678011, "Equipment", ItemClassification.progression, 1),
"Speed Booster": ItemData(8678012, "Equipment", ItemClassification.progression, 1),
"Screw Attack": ItemData(8678013, "Equipment", ItemClassification.progression, 1),
"Varia Suit": ItemData(8678014, "Equipment", ItemClassification.useful, 1),
"Gravity Suit": ItemData(8678015, "Equipment", ItemClassification.progression, 1),
"Charge Beam": ItemData(8678016, "Beam", ItemClassification.useful, 1),
"Wave Beam": ItemData(8678017, "Beam", ItemClassification.useful, 1),
"Spazer": ItemData(8678018, "Beam", ItemClassification.useful, 1),
"Plasma Beam": ItemData(8678019, "Beam", ItemClassification.useful, 1),
"Ice Beam": ItemData(8678020, "Beam", ItemClassification.progression, 1),
"Equipment Trap": ItemData(8678021, "Trap", ItemClassification.trap),
"Freeze Trap": ItemData(8678022, "Trap", ItemClassification.trap),
"Short Beam": ItemData(8678023, "Trap", ItemClassification.trap),
"EMP Trap": ItemData(8678024, "Trap", ItemClassification.trap),
"Metroid": ItemData(8678025, "MacGuffin", ItemClassification.progression_skip_balancing),
"The Galaxy is at Peace": ItemData(8678026, "Victory", ItemClassification.progression)

}

filler_weights: Dict[str, int] = {
"Missile": 44,
"Super Missile": 10,
"Power Bomb": 10,
"Energy Tank": 10
}
trap_weights: Dict[str, int] = {
"Equipment Trap": 1,
"Freeze Trap": 1,
"Short Beam": 1,
"EMP Trap": 1
}


def get_item_group(item_name: str) -> str:
return item_table[item_name].group


def item_is_filler(item_name: str) -> bool:
return item_table[item_name].classification == ItemClassification.filler


def item_is_trap(item_name: str) -> bool:
return item_table[item_name].classification == ItemClassification.trap


trap_items: List[str] = list(filter(item_is_trap, item_table.keys()))
filler_items: List[str] = list(filter(item_is_filler, item_table.keys()))

item_name_to_id: Dict[str, int] = {name: data.code for name, data in item_table.items()}

item_name_groups: Dict[str, Set[str]] = {
group: set(item_names) for group, item_names in itertools.groupby(item_table, get_item_group)
}
Loading

0 comments on commit e274a53

Please sign in to comment.