feat: split metro and tram
All checks were successful
deploy to cloudflare pages / deploy (push) Successful in 33s
All checks were successful
deploy to cloudflare pages / deploy (push) Successful in 33s
This commit is contained in:
parent
98967bc491
commit
a2c27899f7
7 changed files with 69 additions and 58 deletions
|
@ -46,17 +46,21 @@ export async function saveScore(
|
|||
scoreCalc: (dist: number) => number,
|
||||
db: D1Database,
|
||||
): Promise<CheckResponse | null> {
|
||||
const stop = await findStopByName(stopName);
|
||||
if (stop === null) return null;
|
||||
|
||||
const row = await db
|
||||
.prepare("SELECT id, game_id, stop_name, points FROM round WHERE game_id = ? AND stop_name = ?")
|
||||
.prepare(
|
||||
"SELECT round.id, round.stop_name, round.points, game.stops_type FROM round INNER JOIN game ON game.id = round.game_id WHERE round.game_id = ? AND round.stop_name = ?",
|
||||
)
|
||||
.bind(uuid, stopName)
|
||||
.first();
|
||||
|
||||
if (row === null || row.points !== -1) return null;
|
||||
|
||||
const coords = (stop.geometry as GeoJSON.Point).coordinates;
|
||||
const type = row.stops_type as "metro" | "tram";
|
||||
const stops = (await getMergedStops(type)).filter((f) => f.properties?.nom === stopName);
|
||||
|
||||
if (stops.length === 0) return null;
|
||||
|
||||
const coords = (stops[0].geometry as GeoJSON.Point).coordinates;
|
||||
const latlng: [number, number] = [coords[1], coords[0]];
|
||||
|
||||
const distance = Math.round(distanceCalc(latlng));
|
||||
|
@ -102,6 +106,21 @@ export async function getTram(): Promise<[GeoJSON.Feature, string][]> {
|
|||
return lazyTram;
|
||||
}
|
||||
|
||||
async function getLineCodes(stopsType: "metro" | "tram"): Promise<Set<string>> {
|
||||
let lines;
|
||||
|
||||
switch (stopsType) {
|
||||
case "metro":
|
||||
lines = await getMetro();
|
||||
break;
|
||||
case "tram":
|
||||
lines = await getTram();
|
||||
break;
|
||||
}
|
||||
|
||||
return new Set<string>(lines.map(([f]) => f.properties!.code_ligne));
|
||||
}
|
||||
|
||||
async function getStops(): Promise<GeoJSON.Feature[]> {
|
||||
if (!lazyStops) {
|
||||
const stops: GeoJSON.FeatureCollection = await fetch(stopsUrl).then((r) => r.json());
|
||||
|
@ -111,8 +130,9 @@ async function getStops(): Promise<GeoJSON.Feature[]> {
|
|||
return lazyStops;
|
||||
}
|
||||
|
||||
export async function getMergedStops(lineCodes: Set<string>): Promise<GeoJSON.Feature[]> {
|
||||
export async function getMergedStops(stopsType: "metro" | "tram"): Promise<GeoJSON.Feature[]> {
|
||||
const stops = await getStops();
|
||||
const lineCodes = await getLineCodes(stopsType);
|
||||
|
||||
const crossingStops = stops.filter((f) => {
|
||||
if (f.properties?.desserte) {
|
||||
|
@ -129,48 +149,40 @@ export async function getMergedStops(lineCodes: Set<string>): Promise<GeoJSON.Fe
|
|||
const mergedStops = Array.from(new Set(crossingStops.map((f) => f.properties?.nom))).map(
|
||||
(nom) => {
|
||||
const matching = crossingStops.filter((f) => f.properties?.nom === nom);
|
||||
return mergeStops(matching)!;
|
||||
|
||||
const longs = matching.map((f) => (f.geometry as GeoJSON.Point).coordinates[0]);
|
||||
const lonAvg = longs.reduce((a, b) => a + b) / longs.length;
|
||||
|
||||
const lats = matching.map((f) => (f.geometry as GeoJSON.Point).coordinates[1]);
|
||||
const latAvg = lats.reduce((a, b) => a + b) / lats.length;
|
||||
|
||||
const desserte = matching.map((f) => f.properties?.desserte).join(",");
|
||||
|
||||
const feature: GeoJSON.Feature = {
|
||||
...matching[0],
|
||||
geometry: { type: "Point", coordinates: [lonAvg, latAvg] },
|
||||
properties: { ...matching[0].properties, desserte },
|
||||
};
|
||||
|
||||
return feature;
|
||||
},
|
||||
);
|
||||
|
||||
return mergedStops;
|
||||
}
|
||||
|
||||
async function findStopByName(name: string): Promise<GeoJSON.Feature | null> {
|
||||
const stops = await getStops();
|
||||
|
||||
return mergeStops(stops.filter((f) => f.properties?.nom === name));
|
||||
}
|
||||
|
||||
function mergeStops(stops: GeoJSON.Feature[]): GeoJSON.Feature | null {
|
||||
if (stops.length === 0) return null;
|
||||
|
||||
const longs = stops.map((f) => (f.geometry as GeoJSON.Point).coordinates[0]);
|
||||
const lonAvg = longs.reduce((a, b) => a + b) / longs.length;
|
||||
|
||||
const lats = stops.map((f) => (f.geometry as GeoJSON.Point).coordinates[1]);
|
||||
const latAvg = lats.reduce((a, b) => a + b) / lats.length;
|
||||
|
||||
const desserte = stops.map((f) => f.properties?.desserte).join(",");
|
||||
|
||||
const feature = stops[0];
|
||||
feature.geometry = { type: "Point", coordinates: [lonAvg, latAvg] };
|
||||
if (feature.properties) feature.properties.desserte = desserte;
|
||||
|
||||
return feature;
|
||||
}
|
||||
|
||||
export function parseOptions(url: URL): GameOptions {
|
||||
const mode = url.searchParams.get("mode");
|
||||
if (mode !== "easy" && mode !== "hard" && mode !== "extreme demon ultra miguel") {
|
||||
error(400, "gamemode is invalid");
|
||||
}
|
||||
|
||||
return {
|
||||
mode,
|
||||
metro: url.searchParams.has("metro"),
|
||||
tram: url.searchParams.has("tram"),
|
||||
};
|
||||
const stopsType = url.searchParams.get("stops_type");
|
||||
if (stopsType !== "metro" && stopsType !== "tram") {
|
||||
error(400, "stops_type is invalid");
|
||||
}
|
||||
|
||||
return { mode, stopsType };
|
||||
}
|
||||
|
||||
// https://underscorejs.org/docs/modules/sample.html
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
export interface GameOptions {
|
||||
mode: "easy" | "hard" | "extreme demon ultra miguel";
|
||||
metro: boolean;
|
||||
tram: boolean;
|
||||
stopsType: "metro" | "tram";
|
||||
}
|
||||
|
||||
export interface MapData {
|
||||
|
|
|
@ -33,10 +33,12 @@
|
|||
</select>
|
||||
</label>
|
||||
|
||||
<div>
|
||||
<label>metro: <input type="checkbox" name="metro" checked /></label>
|
||||
<label>tram: <input type="checkbox" name="tram" /></label>
|
||||
</div>
|
||||
<label>
|
||||
arrets: <select name="stops_type">
|
||||
<option value="metro">Métro</option>
|
||||
<option value="tram">Tram</option>
|
||||
</select>
|
||||
</label>
|
||||
|
||||
<input type="submit" value="LANCER LA PARTIE" />
|
||||
</form>
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { error } from "@sveltejs/kit";
|
||||
import type { RequestHandler } from "./$types";
|
||||
import { createGame, getMergedStops, getMetro, getTram, parseOptions, sample } from "$lib";
|
||||
import { createGame, getMergedStops, parseOptions, sample } from "$lib";
|
||||
|
||||
export const GET: RequestHandler = async ({ url, platform, locals }) => {
|
||||
const db = platform?.env?.TCL_GUESSR_D1 ?? null;
|
||||
|
@ -10,13 +10,8 @@ export const GET: RequestHandler = async ({ url, platform, locals }) => {
|
|||
if (user === null) error(401, "not logged in");
|
||||
|
||||
const options = parseOptions(url);
|
||||
const lineColors: [GeoJSON.Feature, string][] = [];
|
||||
|
||||
if (options.metro) lineColors.push(...(await getMetro()));
|
||||
if (options.tram) lineColors.push(...(await getTram()));
|
||||
|
||||
const lineCodes = new Set<string>(lineColors.map(([f]) => f.properties!.code_ligne));
|
||||
const crossingStops = await getMergedStops(lineCodes);
|
||||
const crossingStops = await getMergedStops(options.stopsType);
|
||||
|
||||
const randomStops = sample(crossingStops, 5);
|
||||
if (!randomStops) {
|
||||
|
|
|
@ -7,16 +7,17 @@ export const GET: RequestHandler = async ({ url }) => {
|
|||
const mapData: MapData = { lines: [], stops: [] };
|
||||
|
||||
if (options.mode !== "extreme demon ultra miguel") {
|
||||
const lineColors: [GeoJSON.Feature, string][] = [];
|
||||
|
||||
if (options.metro) lineColors.push(...(await getMetro()));
|
||||
if (options.tram) lineColors.push(...(await getTram()));
|
||||
|
||||
mapData.lines = lineColors;
|
||||
switch (options.stopsType) {
|
||||
case "metro":
|
||||
mapData.lines = await getMetro();
|
||||
break;
|
||||
case "tram":
|
||||
mapData.lines = await getTram();
|
||||
break;
|
||||
}
|
||||
|
||||
if (options.mode === "easy") {
|
||||
const lineCodes = new Set<string>(lineColors.map(([f]) => f.properties!.code_ligne));
|
||||
const crossingStops = await getMergedStops(lineCodes);
|
||||
const crossingStops = await getMergedStops(options.stopsType);
|
||||
|
||||
const strippedStops: [number, number][] = crossingStops.map((f) => {
|
||||
const coords = (f.geometry as GeoJSON.Point).coordinates;
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
<script lang="ts">
|
||||
import type { CheckData, CheckResponse, ClientGameData, MapData } from "$lib/types";
|
||||
import { goto } from "$app/navigation";
|
||||
import { page } from "$app/stores";
|
||||
import L from "leaflet";
|
||||
|
||||
import "leaflet/dist/leaflet.css";
|
||||
import "leaflet-defaulticon-compatibility/dist/leaflet-defaulticon-compatibility.css";
|
||||
import "leaflet-defaulticon-compatibility";
|
||||
import { goto } from "$app/navigation";
|
||||
|
||||
const zoom = 13;
|
||||
const center: [number, number] = [45.742858495, 4.86163814];
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue