You've already forked luminescent-team-dev
mirror of
https://github.com/TeamLumi/luminescent-team-dev.git
synced 2026-07-09 18:19:19 -07:00
Merge pull request #39 from TeamLumi/trainer-URL-query
Add trainer url query and trainer search bar
This commit is contained in:
@@ -5,6 +5,7 @@ import useIsBrowser from '@docusaurus/useIsBrowser';
|
||||
import {
|
||||
sortedCoordinates,
|
||||
getSelectedLocation,
|
||||
getLocationCoordsFromZoneId,
|
||||
} from './coordinates';
|
||||
import { SearchBar } from './SearchBar';
|
||||
import { MapperTabPanel } from './TabPanel/MapperTabPanel';
|
||||
@@ -14,6 +15,9 @@ import './style.css';
|
||||
import {
|
||||
getAreaEncounters,
|
||||
getTrainersFromZoneId,
|
||||
getZoneIdFromTrainerId,
|
||||
getFullTrainerById,
|
||||
getAllTrainers,
|
||||
getFieldItemsFromZoneID,
|
||||
getHiddenItemsFromZoneID,
|
||||
getPokemonIdFromName
|
||||
@@ -50,13 +54,7 @@ const canvasDimensions = {
|
||||
height: 720
|
||||
}
|
||||
|
||||
const versionNumber = "Beta 1.2.0";
|
||||
|
||||
export const CLEAR_MODE = {
|
||||
HIGHLIGHT: "highlight",
|
||||
SELECT: "select",
|
||||
ENCOUNTER: "enc",
|
||||
};
|
||||
const versionNumber = "Beta 1.2.1";
|
||||
|
||||
export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
const isBrowser = useIsBrowser();
|
||||
@@ -83,6 +81,9 @@ export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
const [trainerList, setTrainerList] = useState([]);
|
||||
const [showTrainerModal, setShowTrainerModal] = useState(false);
|
||||
|
||||
const [searchBarTrainer, setSearchBarTrainer] = useState(null);
|
||||
const skipSearchClear = useRef(false);
|
||||
|
||||
const [showSettings, setShowSettings] = useState(false);
|
||||
const [colors, setColors] = useState({
|
||||
hov: { r: 247, g: 100, b: 200, a: 0.7 },
|
||||
@@ -105,6 +106,37 @@ export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
const [fixedShopList, setFixedShops] = useState([]);
|
||||
const [heartScaleShopList, setHeartScaleShop] = useState([]);
|
||||
|
||||
const [selectedTab, setSelectedTab] = useState(
|
||||
new URLSearchParams(window.location.search).has('trainerId') ? 1 : 0
|
||||
);
|
||||
|
||||
const handleTabChange = (newTab) => {
|
||||
setSelectedTab(newTab);
|
||||
};
|
||||
|
||||
// Handle URL query parameters for trainer ID
|
||||
useEffect(() => {
|
||||
const params = new URLSearchParams(window.location.search);
|
||||
const trainerId = params.get('trainerId');
|
||||
|
||||
if (trainerId) {
|
||||
const zoneId = getZoneIdFromTrainerId(trainerId, GAMEDATA3);
|
||||
if (zoneId) {
|
||||
const location = getLocationCoordsFromZoneId(zoneId);
|
||||
if (location) {
|
||||
setSelectedZone(location.name);
|
||||
}
|
||||
handleSetLocationZoneId(zoneId);
|
||||
|
||||
const trainers = getTrainersFromZoneId(zoneId, GAMEDATA3);
|
||||
const trainer = trainers.find(t => t.trainerId === parseInt(trainerId));
|
||||
if (trainer) {
|
||||
setSelectedTrainer(trainer);
|
||||
setShowTrainerModal(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}, []);
|
||||
const locationId = useRef(null);
|
||||
useEffect(() => {
|
||||
if(locationId !== null) {
|
||||
@@ -116,6 +148,15 @@ export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
setEncounterLocations(getMapperRoutesFromPokemonId(selectedPokemon?.id, GAMEDATA3));
|
||||
}, [selectedPokemon]);
|
||||
|
||||
// Clear SearchBar trainer selection when location or selected trainer changes
|
||||
useEffect(() => {
|
||||
if (skipSearchClear.current) {
|
||||
skipSearchClear.current = false;
|
||||
return;
|
||||
}
|
||||
setSearchBarTrainer(null);
|
||||
}, [selectedZone, selectedTrainer]);
|
||||
|
||||
const openTrainerModal = () => {
|
||||
setShowTrainerModal(true);
|
||||
};
|
||||
@@ -123,6 +164,25 @@ export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
setShowTrainerModal(false);
|
||||
};
|
||||
|
||||
const allTrainers = React.useMemo(() => getAllTrainers(GAMEDATA3), []);
|
||||
|
||||
const handleTrainerSelect = (trainer) => {
|
||||
skipSearchClear.current = true;
|
||||
setSearchBarTrainer(trainer);
|
||||
const zoneId = trainer.zoneId;
|
||||
if (zoneId || zoneId === 0) {
|
||||
const location = getLocationCoordsFromZoneId(zoneId);
|
||||
if (location) {
|
||||
setSelectedZone(location.name);
|
||||
}
|
||||
handleSetLocationZoneId(zoneId);
|
||||
const fullTrainer = getFullTrainerById(trainer.trainerId, GAMEDATA3);
|
||||
setSelectedTrainer(fullTrainer || trainer);
|
||||
setShowTrainerModal(true);
|
||||
setSelectedTab(1);
|
||||
}
|
||||
};
|
||||
|
||||
const handleOptionChange = (option, value) => {
|
||||
setEncOptions({
|
||||
...encOptions,
|
||||
@@ -320,6 +380,8 @@ export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
setSelectedTrainer={setSelectedTrainer}
|
||||
openTrainerModal={openTrainerModal}
|
||||
routeId={selectedLocation}
|
||||
selectedTab={selectedTab}
|
||||
onTabChange={handleTabChange}
|
||||
/>
|
||||
</div>
|
||||
<SearchBar
|
||||
@@ -333,6 +395,10 @@ export const Mapper = ({ pokemonList3, pokemonList, pokemonListV }) => {
|
||||
selectedPokemon={selectedPokemon}
|
||||
setSelectedPokemon={setSelectedPokemon}
|
||||
handleShowSettings={handleShowSettings}
|
||||
allTrainers={allTrainers}
|
||||
onTrainerSelect={handleTrainerSelect}
|
||||
searchBarTrainer={searchBarTrainer}
|
||||
setSearchBarTrainer={setSearchBarTrainer}
|
||||
/>
|
||||
<TrainersModal
|
||||
showModal={showTrainerModal}
|
||||
|
||||
+270
-152
@@ -1,152 +1,270 @@
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import IconButton from '@mui/material/IconButton';
|
||||
import SettingsIcon from '@mui/icons-material/Settings';
|
||||
import { Autocomplete, TextField } from '@mui/material';
|
||||
import Fuse from 'fuse.js';
|
||||
|
||||
import { getLocationCoordsFromName, getLocationNames } from './coordinates';
|
||||
import './style.css';
|
||||
|
||||
const PokemonSearchInput = ({
|
||||
allPokemons,
|
||||
setDebouncedText,
|
||||
selectedPokemon,
|
||||
setSelectedPokemon,
|
||||
}) => {
|
||||
const [searchText, setSearchText] = useState("");
|
||||
|
||||
useEffect(() => {
|
||||
const timer = setTimeout(() => {
|
||||
setDebouncedText(searchText);
|
||||
}, 300);
|
||||
return () => clearTimeout(timer);
|
||||
}, [searchText, setDebouncedText]);
|
||||
|
||||
const handlePokemonNameChange = (_, value, reason) => {
|
||||
if (reason !== "clear" && value) {
|
||||
setSelectedPokemon(value);
|
||||
setSearchText(value?.name ?? "");
|
||||
} else {
|
||||
setSelectedPokemon(null);
|
||||
setSearchText("");
|
||||
}
|
||||
};
|
||||
|
||||
const handleInputChange = (_, value) => {
|
||||
setSearchText(value);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="monSearchBar">
|
||||
<Autocomplete
|
||||
id="pokemon-search-input"
|
||||
clearOnBlur={false}
|
||||
blurOnSelect
|
||||
options={allPokemons}
|
||||
getOptionLabel={(option) => option.name}
|
||||
value={selectedPokemon}
|
||||
onChange={handlePokemonNameChange}
|
||||
inputValue={searchText}
|
||||
onInputChange={handleInputChange}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
label="Search Pokémon Location"
|
||||
fullWidth
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
const LocationNameDropdown = ({
|
||||
locationName,
|
||||
setLocationName,
|
||||
setLocationZoneId,
|
||||
canvasRef
|
||||
}) => {
|
||||
const locations = getLocationNames();
|
||||
const handleLocationChange = (e, value, reason) => {
|
||||
if (reason !== "clear" && value) {
|
||||
setLocationName(value);
|
||||
const location = getLocationCoordsFromName(value);
|
||||
setLocationZoneId(location?.zoneId);
|
||||
} else {
|
||||
setLocationName(null);
|
||||
setLocationZoneId(null);
|
||||
}
|
||||
};
|
||||
|
||||
const defaultOption = locations.length > 0 ? locations[0] : '';
|
||||
return (
|
||||
<div className="location">
|
||||
<Autocomplete
|
||||
id="location-input"
|
||||
clearOnBlur={false}
|
||||
blurOnSelect
|
||||
options={locations}
|
||||
getOptionLabel={(option) => option}
|
||||
value={locationName}
|
||||
onChange={handleLocationChange}
|
||||
inputValue={locationName ?? ""}
|
||||
onInputChange={(_, value) => {
|
||||
setLocationName(value);
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
label="Current Location"
|
||||
fullWidth
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
const SettingsButton = ({handleShowSettings}) => {
|
||||
return (
|
||||
<div className="settings">
|
||||
<IconButton aria-label="settings" onClick={handleShowSettings}>
|
||||
<SettingsIcon />
|
||||
</IconButton>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export const SearchBar = ({
|
||||
canvasDimensions,
|
||||
pokemonList,
|
||||
handleDebouncedTextChange,
|
||||
locationName,
|
||||
setLocationName,
|
||||
setLocationZoneId,
|
||||
canvasRef,
|
||||
selectedPokemon,
|
||||
setSelectedPokemon,
|
||||
handleShowSettings,
|
||||
}) => {
|
||||
return (
|
||||
<div
|
||||
className="infoCol"
|
||||
style={{
|
||||
width: `${canvasDimensions.width}px`,
|
||||
height: `${canvasDimensions.height}px`
|
||||
}}
|
||||
>
|
||||
<PokemonSearchInput
|
||||
allPokemons={pokemonList}
|
||||
setDebouncedText={handleDebouncedTextChange}
|
||||
selectedPokemon={selectedPokemon}
|
||||
setSelectedPokemon={setSelectedPokemon}
|
||||
/>
|
||||
<LocationNameDropdown
|
||||
locationName={locationName}
|
||||
setLocationName={setLocationName}
|
||||
setLocationZoneId={setLocationZoneId}
|
||||
/>
|
||||
<SettingsButton handleShowSettings={handleShowSettings} />
|
||||
</div>
|
||||
)
|
||||
};
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import IconButton from '@mui/material/IconButton';
|
||||
import SettingsIcon from '@mui/icons-material/Settings';
|
||||
import { Autocomplete, TextField } from '@mui/material';
|
||||
import { FixedSizeList } from 'react-window';
|
||||
|
||||
import { getLocationCoordsFromName, getLocationNames } from './coordinates';
|
||||
import './style.css';
|
||||
|
||||
const PokemonSearchInput = ({
|
||||
allPokemons,
|
||||
setDebouncedText,
|
||||
selectedPokemon,
|
||||
setSelectedPokemon,
|
||||
}) => {
|
||||
const [searchText, setSearchText] = useState("");
|
||||
|
||||
useEffect(() => {
|
||||
const timer = setTimeout(() => {
|
||||
setDebouncedText(searchText);
|
||||
}, 300);
|
||||
return () => clearTimeout(timer);
|
||||
}, [searchText, setDebouncedText]);
|
||||
|
||||
const handlePokemonNameChange = (_, value, reason) => {
|
||||
if (reason !== "clear" && value) {
|
||||
setSelectedPokemon(value);
|
||||
setSearchText(value?.name ?? "");
|
||||
} else {
|
||||
setSelectedPokemon(null);
|
||||
setSearchText("");
|
||||
}
|
||||
};
|
||||
|
||||
const handleInputChange = (_, value) => {
|
||||
setSearchText(value);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="monSearchBar">
|
||||
<Autocomplete
|
||||
id="pokemon-search-input"
|
||||
clearOnBlur={false}
|
||||
blurOnSelect
|
||||
options={allPokemons}
|
||||
getOptionLabel={(option) => option.name}
|
||||
value={selectedPokemon}
|
||||
onChange={handlePokemonNameChange}
|
||||
inputValue={searchText}
|
||||
onInputChange={handleInputChange}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
label="Search Pokémon Location"
|
||||
fullWidth
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
const LocationNameDropdown = ({
|
||||
locationName,
|
||||
setLocationName,
|
||||
setLocationZoneId,
|
||||
}) => {
|
||||
const locations = getLocationNames();
|
||||
const handleLocationChange = (e, value, reason) => {
|
||||
if (reason !== "clear" && value) {
|
||||
setLocationName(value);
|
||||
const location = getLocationCoordsFromName(value);
|
||||
setLocationZoneId(location?.zoneId);
|
||||
} else {
|
||||
setLocationName(null);
|
||||
setLocationZoneId(null);
|
||||
}
|
||||
};
|
||||
|
||||
const defaultOption = locations.length > 0 ? locations[0] : '';
|
||||
return (
|
||||
<div className="location">
|
||||
<Autocomplete
|
||||
id="location-input"
|
||||
clearOnBlur={false}
|
||||
blurOnSelect
|
||||
options={locations}
|
||||
getOptionLabel={(option) => option}
|
||||
value={locationName}
|
||||
onChange={handleLocationChange}
|
||||
inputValue={locationName ?? ""}
|
||||
onInputChange={(_, value) => {
|
||||
setLocationName(value);
|
||||
}}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
label="Current Location"
|
||||
fullWidth
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
const LISTBOX_PADDING = 8;
|
||||
const ITEM_SIZE = 48;
|
||||
const MAX_VISIBLE_ITEMS = 14;
|
||||
|
||||
function renderRow(props) {
|
||||
const { data, index, style } = props;
|
||||
const inlineStyle = {
|
||||
...style,
|
||||
top: (style.top ?? 0) + LISTBOX_PADDING,
|
||||
};
|
||||
|
||||
return React.cloneElement(data[index], {
|
||||
style: {
|
||||
...data[index].props.style,
|
||||
...inlineStyle,
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
const OuterElementContext = React.createContext({});
|
||||
|
||||
const OuterElementType = React.forwardRef(function OuterElementType(props, ref) {
|
||||
const outerProps = React.useContext(OuterElementContext);
|
||||
return <div ref={ref} {...props} {...outerProps} />;
|
||||
});
|
||||
|
||||
const ListboxComponent = React.forwardRef(function ListboxComponent(props, ref) {
|
||||
const { children, ...other } = props;
|
||||
const itemData = React.Children.toArray(children);
|
||||
const itemCount = itemData.length;
|
||||
|
||||
const height = itemCount > MAX_VISIBLE_ITEMS
|
||||
? MAX_VISIBLE_ITEMS * ITEM_SIZE + 2 * LISTBOX_PADDING
|
||||
: itemCount * ITEM_SIZE + 2 * LISTBOX_PADDING;
|
||||
|
||||
return (
|
||||
<div ref={ref}>
|
||||
<OuterElementContext.Provider value={other}>
|
||||
<FixedSizeList
|
||||
itemData={itemData}
|
||||
height={height}
|
||||
width="100%"
|
||||
itemSize={ITEM_SIZE}
|
||||
itemCount={itemCount}
|
||||
outerElementType={OuterElementType}
|
||||
innerElementType="ul"
|
||||
>
|
||||
{renderRow}
|
||||
</FixedSizeList>
|
||||
</OuterElementContext.Provider>
|
||||
</div>
|
||||
);
|
||||
});
|
||||
|
||||
const TrainerSearchInput = ({
|
||||
allTrainers,
|
||||
onTrainerSelect,
|
||||
value,
|
||||
onChange,
|
||||
}) => {
|
||||
const [searchText, setSearchText] = useState("");
|
||||
|
||||
// Clear internal text when value is cleared externally
|
||||
useEffect(() => {
|
||||
if (!value) {
|
||||
setSearchText("");
|
||||
}
|
||||
}, [value]);
|
||||
|
||||
const handleTrainerChange = (_, newValue, reason) => {
|
||||
if (reason !== "clear" && newValue) {
|
||||
onChange(newValue);
|
||||
setSearchText(newValue.label);
|
||||
onTrainerSelect(newValue);
|
||||
} else {
|
||||
onChange(null);
|
||||
setSearchText("");
|
||||
}
|
||||
};
|
||||
|
||||
const handleInputChange = (_, newInputValue) => {
|
||||
setSearchText(newInputValue);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="monSearchBar">
|
||||
<Autocomplete
|
||||
id="trainer-search-input"
|
||||
clearOnBlur={false}
|
||||
blurOnSelect
|
||||
options={allTrainers}
|
||||
ListboxComponent={ListboxComponent}
|
||||
getOptionLabel={(option) => option.label}
|
||||
value={value}
|
||||
onChange={handleTrainerChange}
|
||||
inputValue={searchText}
|
||||
onInputChange={handleInputChange}
|
||||
renderInput={(params) => (
|
||||
<TextField
|
||||
{...params}
|
||||
label="Search Trainer"
|
||||
fullWidth
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
const SettingsButton = ({handleShowSettings}) => {
|
||||
return (
|
||||
<div className="settings">
|
||||
<IconButton aria-label="settings" onClick={handleShowSettings}>
|
||||
<SettingsIcon />
|
||||
</IconButton>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export const SearchBar = ({
|
||||
canvasDimensions,
|
||||
pokemonList,
|
||||
handleDebouncedTextChange,
|
||||
locationName,
|
||||
setLocationName,
|
||||
setLocationZoneId,
|
||||
canvasRef,
|
||||
selectedPokemon,
|
||||
setSelectedPokemon,
|
||||
handleShowSettings,
|
||||
allTrainers,
|
||||
onTrainerSelect,
|
||||
searchBarTrainer,
|
||||
setSearchBarTrainer,
|
||||
}) => {
|
||||
return (
|
||||
<div
|
||||
className="infoCol"
|
||||
style={{
|
||||
width: `${canvasDimensions.width}px`,
|
||||
height: `${canvasDimensions.height}px`
|
||||
}}
|
||||
>
|
||||
<PokemonSearchInput
|
||||
allPokemons={pokemonList}
|
||||
setDebouncedText={handleDebouncedTextChange}
|
||||
selectedPokemon={selectedPokemon}
|
||||
setSelectedPokemon={setSelectedPokemon}
|
||||
/>
|
||||
<TrainerSearchInput
|
||||
allTrainers={allTrainers}
|
||||
onTrainerSelect={onTrainerSelect}
|
||||
value={searchBarTrainer}
|
||||
onChange={setSearchBarTrainer}
|
||||
/>
|
||||
<LocationNameDropdown
|
||||
locationName={locationName}
|
||||
setLocationName={setLocationName}
|
||||
setLocationZoneId={setLocationZoneId}
|
||||
/>
|
||||
<SettingsButton handleShowSettings={handleShowSettings} />
|
||||
</div>
|
||||
)
|
||||
};
|
||||
|
||||
@@ -32,7 +32,7 @@ const EncountersPanel = ({ encOptions, handleOptionChange, encounterList, pokemo
|
||||
};
|
||||
|
||||
const getGroundTextColor = () => {
|
||||
if (encounterList.GroundEnc.lenth === 0) {
|
||||
if (encounterList.GroundEnc.length === 0) {
|
||||
return modeChangeTextColor;
|
||||
} else if (groundEncountersIds.includes(routeId)) {
|
||||
return "#000000"
|
||||
|
||||
@@ -16,10 +16,12 @@ export const MapperTabPanel = ({
|
||||
selectedTrainer,
|
||||
setSelectedTrainer,
|
||||
openTrainerModal,
|
||||
routeId
|
||||
routeId,
|
||||
selectedTab,
|
||||
onTabChange,
|
||||
}) => {
|
||||
return (
|
||||
<PokemonTabPanel tabNames={["Encounters", "Trainers", "Items", "Shops"]}>
|
||||
<PokemonTabPanel tabNames={["Encounters", "Trainers", "Items", "Shops"]} selectedTab={selectedTab} onTabChange={onTabChange}>
|
||||
<EncountersPanel
|
||||
encOptions={encOptions}
|
||||
handleOptionChange={handleOptionChange}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import React, { useState } from 'react';
|
||||
import React from 'react';
|
||||
import { Box, Tab, Tabs } from '@mui/material';
|
||||
|
||||
const PokemonPanel = ({ id, selectedTab, children }) => {
|
||||
@@ -30,11 +30,14 @@ const PokemonTabs = ({ tabNames, selectedTab, handleTabChange }) => {
|
||||
|
||||
const PokemonTabPanel = ({
|
||||
tabNames,
|
||||
children
|
||||
children,
|
||||
selectedTab = 0,
|
||||
onTabChange,
|
||||
}) => {
|
||||
const [selectedTab, setSelectedTab] = useState(0);
|
||||
const handleTabChange = (event, newTab) => {
|
||||
setSelectedTab(newTab);
|
||||
if (onTabChange) {
|
||||
onTabChange(newTab);
|
||||
}
|
||||
};
|
||||
|
||||
return (
|
||||
|
||||
@@ -53,7 +53,7 @@ export const TrainerDropdown = ({ trainer, setTrainer, trainerList, smallest })
|
||||
<Autocomplete
|
||||
id="trainer-input"
|
||||
options={[defaultTrainer, ...trainerList]}
|
||||
getOptionLabel={(option) => `${option.team_name} (${option.trainer_id})`}
|
||||
getOptionLabel={(option) => `${option.team_name} (${option.trainerId ?? option.trainer_id})`}
|
||||
defaultValue={defaultTrainer}
|
||||
value={trainer}
|
||||
onChange={(e, value) => setTrainer(value)}
|
||||
|
||||
@@ -31,9 +31,9 @@ const TrainersModal = ({
|
||||
};
|
||||
|
||||
const handleOpenShowdown = () => {
|
||||
if (!selectedTrainer?.trainer_id) return;
|
||||
if (!selectedTrainer?.trainerId) return;
|
||||
|
||||
const url = `https://calc.relumishowdown.dpdns.org/?mode=ingame&setSource=ingame&trainerId=${selectedTrainer.trainer_id}`;
|
||||
const url = `https://calc.relumishowdown.dpdns.org/?mode=ingame&setSource=ingame&trainerId=${selectedTrainer.trainerId}`;
|
||||
window.open(url, '_blank', 'noopener,noreferrer');
|
||||
};
|
||||
|
||||
@@ -69,7 +69,7 @@ ${moves}`;
|
||||
maxWidth="1108px"
|
||||
>
|
||||
<DialogTitle>
|
||||
Trainer: {selectedTrainer?.team_name} ({selectedTrainer?.trainer_id})
|
||||
Trainer: {selectedTrainer?.team_name} ({selectedTrainer?.trainerId})
|
||||
</DialogTitle>
|
||||
<IconButton
|
||||
aria-label="close"
|
||||
@@ -98,7 +98,7 @@ ${moves}`;
|
||||
<IconButton
|
||||
aria-label="Open In Showdown"
|
||||
onClick={handleOpenShowdown}
|
||||
to={`https://calc.relumishowdown.dpdns.org/?mode=ingame&setSource=ingame&trainerId=` + selectedTrainer?.trainer_id}
|
||||
to={`https://calc.relumishowdown.dpdns.org/?mode=ingame&setSource=ingame&trainerId=` + selectedTrainer?.trainerId}
|
||||
sx={{
|
||||
position: 'absolute',
|
||||
right: 108,
|
||||
|
||||
@@ -53,11 +53,13 @@
|
||||
.infoCol {
|
||||
position: absolute;
|
||||
top: 122px;
|
||||
justify-content: end;
|
||||
display: grid;
|
||||
grid-template-rows: 60px 25px;
|
||||
grid-template-rows: auto auto auto;
|
||||
align-content: start;
|
||||
justify-content: end;
|
||||
pointer-events: none;
|
||||
touch-action: manipulation;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.monSearchBar {
|
||||
@@ -69,18 +71,16 @@
|
||||
|
||||
.location {
|
||||
pointer-events: auto;
|
||||
margin-top: 16px;
|
||||
margin-top: 10px;
|
||||
margin-right: 10px;
|
||||
}
|
||||
|
||||
.settings {
|
||||
display: grid;
|
||||
align-content: end;
|
||||
justify-content: end;
|
||||
position: absolute;
|
||||
bottom: 10px;
|
||||
right: 10px;
|
||||
width: fit-content;
|
||||
height: fit-content;
|
||||
margin-left: 16rem;
|
||||
margin-top: 36rem;
|
||||
pointer-events: auto;
|
||||
}
|
||||
|
||||
|
||||
@@ -51,7 +51,7 @@ import {
|
||||
getTimeOfDayEncounters,
|
||||
getAllHoneyTreeEncounters
|
||||
} from './encounters'
|
||||
import { getTrainersFromZoneId } from './trainers';
|
||||
import { getTrainersFromZoneId, getZoneIdFromTrainerId, getFullTrainerById, getAllTrainers } from './trainers';
|
||||
import { getFieldItemsFromZoneID, getHiddenItemsFromZoneID } from './location';
|
||||
import { getEvolutionTree } from './evolution';
|
||||
import { getEggGroupNameById, getEggGroupViaPokemonId } from './egggroup';
|
||||
@@ -196,6 +196,9 @@ export {
|
||||
getTimeOfDayEncounters,
|
||||
getAllHoneyTreeEncounters,
|
||||
getTrainersFromZoneId,
|
||||
getZoneIdFromTrainerId,
|
||||
getFullTrainerById,
|
||||
getAllTrainers,
|
||||
getFieldItemsFromZoneID,
|
||||
getHiddenItemsFromZoneID
|
||||
};
|
||||
|
||||
@@ -9,12 +9,65 @@ function getTrainersFromZoneId(zoneId, mode = GAMEDATA2) {
|
||||
zoneKey = "326" // To be at the Lake Valor After for ease of use.
|
||||
}
|
||||
if (zoneKey in TrainerLocations[mode]) {
|
||||
return TrainerLocations[mode][zoneKey];
|
||||
return TrainerLocations[mode][zoneKey].map(t => ({ ...t, trainerId: t.trainer_id }));
|
||||
}
|
||||
console.warn(`${zoneKey} is not in the Trainer List.`);
|
||||
return [];
|
||||
};
|
||||
|
||||
function getZoneIdFromTrainerId(trainerId, mode = GAMEDATA2) {
|
||||
if (!trainerId) return null;
|
||||
|
||||
for (const zoneKey in TrainerLocations[mode]) {
|
||||
const trainers = TrainerLocations[mode][zoneKey];
|
||||
const trainer = trainers.find(t => t.trainer_id === parseInt(trainerId));
|
||||
if (trainer) {
|
||||
return parseInt(zoneKey);
|
||||
}
|
||||
}
|
||||
|
||||
console.warn(`Trainer ID ${trainerId} not found in any zone.`);
|
||||
return null;
|
||||
};
|
||||
|
||||
function getFullTrainerById(trainerId, mode = GAMEDATA2) {
|
||||
if (!trainerId) return null;
|
||||
|
||||
for (const zoneKey in TrainerLocations[mode]) {
|
||||
const trainers = TrainerLocations[mode][zoneKey];
|
||||
const trainer = trainers.find(t => t.trainer_id === parseInt(trainerId));
|
||||
if (trainer) {
|
||||
return { ...trainer, trainerId: trainer.trainer_id, zoneId: parseInt(zoneKey) };
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
};
|
||||
|
||||
function getAllTrainers(mode = GAMEDATA2) {
|
||||
const seen = new Set();
|
||||
const trainers = [];
|
||||
for (const zoneKey in TrainerLocations[mode]) {
|
||||
for (const trainer of TrainerLocations[mode][zoneKey]) {
|
||||
if (seen.has(trainer.trainer_id)) continue;
|
||||
seen.add(trainer.trainer_id);
|
||||
trainers.push({
|
||||
trainerId: trainer.trainer_id,
|
||||
zoneId: parseInt(zoneKey),
|
||||
name: trainer.name,
|
||||
route: trainer.route,
|
||||
team_name: trainer.team_name,
|
||||
trainerType: trainer.trainerType,
|
||||
label: `${trainer.team_name} (${trainer.trainer_id})`,
|
||||
});
|
||||
}
|
||||
}
|
||||
return trainers;
|
||||
};
|
||||
|
||||
export {
|
||||
getTrainersFromZoneId
|
||||
}
|
||||
getTrainersFromZoneId,
|
||||
getZoneIdFromTrainerId,
|
||||
getFullTrainerById,
|
||||
getAllTrainers,
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user