Skip to content

Commit

Permalink
Merge branch 'navigation-search' of github.com:Thorium-Sim/thorium-no…
Browse files Browse the repository at this point in the history
…va into waypoint-list
  • Loading branch information
alexanderson1993 committed Aug 2, 2022
2 parents e8e058c + 528e843 commit 51a15c7
Show file tree
Hide file tree
Showing 11 changed files with 360 additions and 28 deletions.
51 changes: 50 additions & 1 deletion client/src/cards/ComponentDemo/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ import SearchableList from "@thorium/ui/SearchableList";
import InfoTip from "@thorium/ui/InfoTip";
import TagInput from "@thorium/ui/TagInput";
import Button from "@thorium/ui/Button";
import SearchableInput, {DefaultResultLabel} from "@thorium/ui/SearchableInput";
import {QueryFunctionContext} from "@tanstack/react-query";

const ModalDemo = ({title, children}: {title: string; children: ReactNode}) => {
const [isOpen, setIsOpen] = useState(false);
Expand Down Expand Up @@ -78,7 +80,38 @@ const TagInputDemo = () => {
/>
);
};

async function searchableInputQuery({
queryKey,
}: QueryFunctionContext<[string, string]>) {
await new Promise(res => setTimeout(res, 1000 + Math.random() * 500));
const [key, query] = queryKey;
const people = [
{id: 1, name: "Wade Cooper"},
{id: 2, name: "Arlene Mccoy"},
{id: 3, name: "Devon Webb"},
{id: 4, name: "Tom Cook"},
{id: 5, name: "Tanya Fox"},
{id: 6, name: "Hellen Schmidt"},
];

const filteredPeople =
query === ""
? people
: people.filter(person =>
person.name
.toLowerCase()
.replace(/\s+/g, "")
.includes(query.toLowerCase().replace(/\s+/g, ""))
);

return filteredPeople;
}

export default function ComponentDemo() {
const [selected, setSelected] = useState<null | {id: number; name: string}>(
null
);
return (
<div className="flex flex-col gap-8 text-white h-full overflow-y-auto">
<div className="flex flex-col gap-4">
Expand Down Expand Up @@ -114,7 +147,23 @@ export default function ComponentDemo() {
</div>
</div>
</div>

<div>
<h2 className="text-3xl">Searchable Input</h2>
<SearchableInput
key="demo"
selected={selected}
setSelected={val => {
setSelected(val);
}}
getOptions={searchableInputQuery}
displayValue={result => result?.name}
ResultLabel={({result, active, selected}) => (
<DefaultResultLabel active={active} selected={selected}>
{result.name}
</DefaultResultLabel>
)}
/>
</div>
<div>
<h2 className="text-3xl">Badges</h2>
<div className="flex gap-4">
Expand Down
6 changes: 5 additions & 1 deletion client/src/cards/Navigation/InterstellarWrapper.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import {useGetStarmapStore} from "client/src/components/Starmap/starmapStore";
import {useNetRequest} from "client/src/context/useNetRequest";
import {InterstellarMap} from "client/src/components/Starmap/InterstellarMap";
import SystemMarker from "client/src/components/Starmap/SystemMarker";
import {Suspense} from "react";
import {Suspense, useEffect} from "react";
import {ErrorBoundary} from "react-error-boundary";
import {StarmapShip} from "client/src/components/Starmap/StarmapShip";
import {WaypointEntity} from "client/src/components/Starmap/WaypointEntity";
Expand All @@ -14,6 +14,10 @@ export function InterstellarWrapper() {
const ship = useNetRequest("navigationShip");

const waypoints = useNetRequest("waypoints", {systemId: null});
useEffect(() => {
useStarmapStore.getState().currentSystemSet?.(null);
}, []);

return (
<InterstellarMap>
{starmapSystems.map(sys =>
Expand Down
7 changes: 6 additions & 1 deletion client/src/cards/Navigation/SolarSystemWrapper.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import {useGetStarmapStore} from "client/src/components/Starmap/starmapStore";
import {useNetRequest} from "client/src/context/useNetRequest";
import {useRef} from "react";
import {useEffect, useRef} from "react";
import {SolarSystemMap} from "client/src/components/Starmap/SolarSystemMap";
import {Suspense} from "react";
import {Color, Group, Vector3} from "three";
Expand All @@ -25,6 +25,11 @@ export function SolarSystemWrapper() {
const currentSystem = useStarmapStore(store => store.currentSystem);

if (currentSystem === null) throw new Error("No current system");

useEffect(() => {
useStarmapStore.getState().currentSystemSet?.(currentSystem);
}, []);

const system = useNetRequest("starmapSystem", {systemId: currentSystem});
const starmapEntities = useNetRequest("starmapSystemEntities", {
systemId: currentSystem,
Expand Down
74 changes: 74 additions & 0 deletions client/src/cards/Navigation/data.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import {
solarRadiusToKilometers,
} from "server/src/utils/unitTypes";
import {Vector3} from "three";
import {matchSorter} from "match-sorter";

type Waypoint = {
id: number;
Expand Down Expand Up @@ -133,6 +134,79 @@ export const requests = {
);
return waypoints || [];
},
navigationSearch: async (
context: DataContext,
params: {query: string},
publishParams: null
) => {
if (publishParams !== null) throw null;
const {query} = params;

// Get all of the planet, star, and solar system entities that match the query.
const matchItems = matchSorter(
context.flight?.ecs.entities
.filter(
e =>
e.components.isStar ||
e.components.isPlanet ||
e.components.isSolarSystem
)
.map(m => {
let position = m.components.position;
if (!position) {
const {x, y, z} = getCompletePositionFromOrbit(m);
const parentId = getObjectSystem(m)?.id || null;
position = {
x,
y,
z,
type: m.components.isSolarSystem ? "interstellar" : "solar",
parentId: m.components.isSolarSystem ? null : parentId,
};
}
return {
...m,
type: m.components.isSolarSystem
? "solar"
: m.components.isPlanet
? "planet"
: m.components.isShip
? "ship"
: "star",
name: m.components.identity!.name,
description: m.components.identity?.description,
temperature: m.components.temperature?.temperature,
spectralType: m.components.isStar?.spectralType,
classification: m.components.isPlanet?.classification,
mass:
m.components.isStar?.solarMass ||
m.components.isPlanet?.terranMass,
population: m.components.population?.count,
position,
} as const;
}) || [],
query,
{
keys: [
"name",
"description",
"temperature",
"spectralType",
"classification",
"mass",
"population",
],
}
).map(m => ({
// TODO Aug 1 2022 - Add in a distance calculation.
id: m.id,
name: m.name,
position: m.position,
type: m.type,
}));

return matchItems;
},
};

export function dataStream(entity: Entity, context: DataContext): boolean {
Expand Down
59 changes: 53 additions & 6 deletions client/src/cards/Navigation/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ import Button from "@thorium/ui/Button";
import {netSend} from "client/src/context/netSend";
import {toast} from "client/src/context/ToastContext";
import {useDataStream} from "client/src/context/useDataStream";
import SearchableInput, {DefaultResultLabel} from "@thorium/ui/SearchableInput";
import {netRequest} from "client/src/context/useNetRequest";
import {capitalCase} from "change-case";

export function Navigation(props: CardProps) {
useDataStream();
Expand All @@ -23,12 +26,9 @@ export function Navigation(props: CardProps) {
<div className="mx-auto h-full bg-black/70 border border-white/50 relative">
<CanvasWrapper shouldRender={props.cardLoaded} />
<div className="grid grid-cols-2 grid-rows-2 absolute inset-0 pointer-events-none p-4">
<Input
label="Search"
labelHidden
placeholder="Search..."
className="pointer-events-auto max-w-sm"
/>
<div className="pointer-events-auto max-w-sm">
<StarmapSearch />
</div>
<div className="w-96 self-start justify-self-end max-h-min">
<ObjectDetails />
<AddWaypoint />{" "}
Expand Down Expand Up @@ -64,6 +64,53 @@ function AddWaypoint() {
</Button>
);
}
function StarmapSearch() {
const useStarmapStore = useGetStarmapStore();
return (
<SearchableInput<{id: number; name: string; type: string; position: any}>
queryKey="nav"
getOptions={async ({queryKey, signal}) => {
const result = await netRequest(
"navigationSearch",
{query: queryKey[1]},
{signal}
);
return result;
}}
ResultLabel={({active, result, selected}) => (
<DefaultResultLabel active={active} selected={selected}>
<p>{result.name}</p>
<p>
<small>
{result.type === "solar"
? "Solar System"
: capitalCase(result.type)}
</small>
</p>
</DefaultResultLabel>
)}
setSelected={async item => {
if (!item) return;
if (
useStarmapStore.getState().currentSystem !== item?.position.parentId
) {
await useStarmapStore
.getState()
.setCurrentSystem(item?.position.parentId);
}
useStarmapStore.setState({selectedObjectId: item.id});
const controls = useStarmapStore.getState().cameraControls;
controls?.current?.moveTo(
item.position.x,
item.position.y,
item.position.z,
true
);
}}
placeholder="Search..."
/>
);
}

function CanvasWrapper({shouldRender}: {shouldRender: boolean}) {
const useStarmapStore = useGetStarmapStore();
Expand Down
18 changes: 14 additions & 4 deletions client/src/components/Starmap/starmapStore.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,14 @@ interface StarmapStore {
setCameraView: (view: "2d" | "3d") => void;
/** Used for core */
currentSystem: number | null;
setCurrentSystem: (systemId: number | null) => void;
setCurrentSystem: (systemId: number | null) => Promise<void>;
currentSystemSet?: (value: any) => void;
cameraVerticalDistance: number;
cameraControls?: MutableRefObject<CameraControls | null>;
}
let storeCount = 0;
const createStarmapStore = () =>
create<StarmapStore>(set => ({
create<StarmapStore>((set, get) => ({
storeCount: storeCount++,
skyboxKey: "blank",
viewingMode: "editor",
Expand All @@ -40,8 +41,17 @@ const createStarmapStore = () =>
cameraView: "3d",
setCameraView: (view: "2d" | "3d") => set({cameraView: view}),
currentSystem: null,
setCurrentSystem: (systemId: number | null) =>
set({currentSystem: systemId}),
setCurrentSystem: async (systemId: number | null) => {
// Resolve the previous promise if it exists
if (get().currentSystemSet) {
get().currentSystemSet?.(null);
}

let currentSystemSet = (value: any) => {};
let promise = new Promise(res => (currentSystemSet = res));
set({currentSystemSet, currentSystem: systemId});
await promise;
},
cameraVerticalDistance: 0,
}));

Expand Down
Loading

0 comments on commit 51a15c7

Please sign in to comment.