Ajout des commandes de creation de rencontre/NJ
This commit is contained in:
131
scripts/travellerMapApi.js
Normal file
131
scripts/travellerMapApi.js
Normal file
@@ -0,0 +1,131 @@
|
||||
/**
|
||||
* MGT2 Commerce – Client API Traveller Map
|
||||
*
|
||||
* Documentation : https://travellermap.com/doc/api
|
||||
*
|
||||
* Deux fonctions exportées :
|
||||
* searchWorlds(query) → [{name, sector, hex, uwp, zone}]
|
||||
* fetchWorldDetail(sector, hex) → {uwp, zone} (zone: 'normal'|'amber'|'red')
|
||||
*/
|
||||
|
||||
const BASE_URL = 'https://travellermap.com';
|
||||
|
||||
/** Convertit la zone Traveller Map ('A', 'R', '') vers notre convention. */
|
||||
function normalizeZone(z) {
|
||||
if (z === 'A') return 'amber';
|
||||
if (z === 'R') return 'red';
|
||||
return 'normal';
|
||||
}
|
||||
|
||||
/**
|
||||
* Recherche des mondes par nom via l'API Traveller Map.
|
||||
*
|
||||
* @param {string} query Nom partiel ou complet (ex. "Regina")
|
||||
* @returns {Promise<Array<{name:string, sector:string, hex:string, uwp:string}>>}
|
||||
* Tableau de résultats (uniquement les mondes, pas secteurs/subsecteurs).
|
||||
* Vide si erreur réseau.
|
||||
*/
|
||||
export async function searchWorlds(query) {
|
||||
if (!query || query.trim().length < 2) return [];
|
||||
|
||||
const url = `${BASE_URL}/api/search?q=${encodeURIComponent(query.trim())}`;
|
||||
|
||||
let data;
|
||||
try {
|
||||
const resp = await fetch(url);
|
||||
if (!resp.ok) throw new Error(`HTTP ${resp.status}`);
|
||||
data = await resp.json();
|
||||
} catch (err) {
|
||||
console.warn('MGT2 Commerce | Traveller Map search error:', err);
|
||||
return [];
|
||||
}
|
||||
|
||||
const items = data?.Results?.Items ?? [];
|
||||
return items
|
||||
.filter(item => item.World) // garder uniquement les mondes
|
||||
.map(item => {
|
||||
const w = item.World;
|
||||
// Formatter le code hex sur 4 chiffres (HexX→XX, HexY→YY)
|
||||
const hex = String(w.HexX).padStart(2, '0') + String(w.HexY).padStart(2, '0');
|
||||
return {
|
||||
name: w.Name,
|
||||
sector: w.Sector,
|
||||
hex,
|
||||
uwp: w.Uwp ?? '',
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Récupère les coordonnées absolues d'un monde en parsecs.
|
||||
* Utilise l'endpoint /api/coordinates.
|
||||
*
|
||||
* @param {string} sector Nom du secteur (ex. "Spinward Marches")
|
||||
* @param {string} hex Code hex 4 chiffres (ex. "1910")
|
||||
* @returns {Promise<{x:number, y:number}|null>}
|
||||
*/
|
||||
export async function fetchWorldCoordinates(sector, hex) {
|
||||
const url = `${BASE_URL}/api/coordinates?sector=${encodeURIComponent(sector)}&hex=${encodeURIComponent(hex)}`;
|
||||
|
||||
try {
|
||||
const resp = await fetch(url);
|
||||
if (!resp.ok) throw new Error(`HTTP ${resp.status}`);
|
||||
const data = await resp.json();
|
||||
if (data?.x == null || data?.y == null) return null;
|
||||
return { x: data.x, y: data.y };
|
||||
} catch (err) {
|
||||
console.warn('MGT2 Commerce | Traveller Map coordinates error:', err);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Calcule la distance en parsecs entre deux mondes à partir de leurs
|
||||
* coordonnées absolues (retournées par fetchWorldCoordinates).
|
||||
* Utilise la formule de distance en coordonnées cubiques pour grille hexagonale.
|
||||
*
|
||||
* Dans le système Traveller Map : les colonnes impaires (hx impair) sont
|
||||
* décalées vers le bas. En coordonnées API, hx impair ↔ x pair.
|
||||
* Conversion offset→cube : q=x, r=y−⌈x/2⌉, s=−q−r.
|
||||
* Distance = max(|Δq|, |Δr|, |Δs|).
|
||||
*
|
||||
* @param {{x:number,y:number}} c1
|
||||
* @param {{x:number,y:number}} c2
|
||||
* @returns {number} Distance en parsecs (entier, minimum 1)
|
||||
*/
|
||||
export function calcParsecs(c1, c2) {
|
||||
const q1 = c1.x, r1 = c1.y - Math.ceil(c1.x / 2);
|
||||
const q2 = c2.x, r2 = c2.y - Math.ceil(c2.x / 2);
|
||||
const dq = q2 - q1, dr = r2 - r1, ds = -dq - dr;
|
||||
return Math.max(1, Math.max(Math.abs(dq), Math.abs(dr), Math.abs(ds)));
|
||||
}
|
||||
|
||||
/**
|
||||
* Récupère les détails d'un monde pour obtenir la zone de voyage.
|
||||
* Utilise l'endpoint /data/{sector}/{hex} (jump=0).
|
||||
*
|
||||
* @param {string} sector Nom du secteur (ex. "Spinward Marches")
|
||||
* @param {string} hex Code hex 4 chiffres (ex. "1910")
|
||||
* @returns {Promise<{uwp:string, zone:string}>}
|
||||
*/
|
||||
export async function fetchWorldDetail(sector, hex) {
|
||||
const url = `${BASE_URL}/data/${encodeURIComponent(sector)}/${hex}`;
|
||||
|
||||
let data;
|
||||
try {
|
||||
const resp = await fetch(url);
|
||||
if (!resp.ok) throw new Error(`HTTP ${resp.status}`);
|
||||
data = await resp.json();
|
||||
} catch (err) {
|
||||
console.warn('MGT2 Commerce | Traveller Map detail error:', err);
|
||||
return null;
|
||||
}
|
||||
|
||||
const world = data?.Worlds?.[0];
|
||||
if (!world) return null;
|
||||
|
||||
return {
|
||||
uwp: world.UWP ?? '',
|
||||
zone: normalizeZone(world.Zone ?? ''),
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user