-
Notifications
You must be signed in to change notification settings - Fork 40
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
front: implement macro editor OP import
- Loading branch information
Showing
3 changed files
with
166 additions
and
0 deletions.
There are no files selected for viewing
130 changes: 130 additions & 0 deletions
130
front/src/applications/operationalStudies/components/MacroEditor/import.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,130 @@ | ||
import { osrdEditoastApi } from 'common/api/osrdEditoastApi'; | ||
import type { SearchResultItemOperationalPoint, SearchPayload } from 'common/api/osrdEditoastApi'; | ||
import type { AppDispatch } from 'store'; | ||
|
||
import type { Node } from './types'; | ||
|
||
const convertGeoCoords = (nodes: Node[]) => { | ||
const xCoords = nodes.map((node) => node.positionX); | ||
const yCoords = nodes.map((node) => node.positionY); | ||
const minX = Math.min(...xCoords); | ||
const minY = Math.min(...yCoords); | ||
const maxX = Math.max(...xCoords); | ||
const maxY = Math.max(...yCoords); | ||
const width = maxX - minX; | ||
const height = maxY - minY; | ||
// TODO: grab NGE component size | ||
const scaleX = 800; | ||
const scaleY = 500; | ||
const padding = 0.1; | ||
|
||
return nodes.map((node) => { | ||
const normalizedX = (node.positionX - minX) / width; | ||
const normalizedY = (node.positionY - minY) / height; | ||
const paddedX = normalizedX * (1 - 2 * padding) + padding; | ||
const paddedY = normalizedY * (1 - 2 * padding) + padding; | ||
return { | ||
...node, | ||
positionX: scaleX * paddedX, | ||
positionY: scaleY * paddedY, | ||
}; | ||
}); | ||
}; | ||
|
||
const importTimetable = async (infraId: number, timetableId: number, dispatch: AppDispatch) => { | ||
const timetablePromise = dispatch( | ||
osrdEditoastApi.endpoints.getV2TimetableById.initiate({ id: timetableId }) | ||
); | ||
const { train_ids } = await timetablePromise.unwrap(); | ||
|
||
const trainSchedulesPromise = dispatch( | ||
osrdEditoastApi.endpoints.postV2TrainSchedule.initiate({ | ||
body: { ids: train_ids }, | ||
}) | ||
); | ||
const trainSchedules = await trainSchedulesPromise.unwrap(); | ||
|
||
// Collect UICs, trigrams and operational point IDs | ||
const pathItems = trainSchedules.map((schedule) => schedule.path).flat(); | ||
const uics = new Set<number>(); | ||
const trigrams = new Set<string>(); | ||
const opIds = new Set<string>(); | ||
// eslint-disable-next-line no-restricted-syntax | ||
for (const item of pathItems) { | ||
if ('uic' in item) { | ||
uics.add(item.uic); | ||
} else if ('trigram' in item) { | ||
trigrams.add(item.trigram); | ||
} else if ('operational_point' in item) { | ||
opIds.add(item.operational_point); | ||
} | ||
} | ||
|
||
if (uics.size === 0 && trigrams.size === 0 && opIds.size === 0) { | ||
return []; | ||
} | ||
|
||
const filterChs = ['BV', '00']; // we're only interested in stations | ||
const searchPayload: SearchPayload = { | ||
object: 'operationalpoint', | ||
query: [ | ||
'and', | ||
['=', ['infra_id'], infraId], | ||
['or', ...filterChs.map((ch) => ['=', ['ch'], ch])], | ||
[ | ||
'or', | ||
...[...uics].map((uic) => ['=', ['uic'], uic]), | ||
...[...trigrams].map((trigram) => ['=', ['trigram'], trigram]), | ||
...[...opIds].map((id) => ['=', ['obj_id'], id]), | ||
], | ||
], | ||
}; | ||
|
||
const searchResults = []; | ||
const pageSize = 100; | ||
let done = false; | ||
for (let page = 1; !done; page += 1) { | ||
const searchPromise = dispatch( | ||
osrdEditoastApi.endpoints.postSearch.initiate({ | ||
page, | ||
pageSize, | ||
searchPayload, | ||
}) | ||
); | ||
// eslint-disable-next-line no-await-in-loop | ||
const results = await searchPromise.unwrap(); | ||
searchResults.push(...results); | ||
done = results.length < pageSize; | ||
} | ||
|
||
let nodes: Node[] = searchResults.map((searchResult) => { | ||
const op = searchResult as SearchResultItemOperationalPoint; | ||
return { | ||
id: op.obj_id, | ||
betriebspunktName: op.trigram, | ||
fullName: op.name, | ||
positionX: op.geographic.coordinates[0], | ||
positionY: op.geographic.coordinates[1], | ||
ports: [], | ||
transitions: [], | ||
connections: [], | ||
resourceId: 1, | ||
perronkanten: 10, | ||
connectionTime: 0, | ||
trainrunCategoryHaltezeiten: {}, | ||
symmetryAxis: 0, | ||
warnings: [], | ||
labelIds: [], | ||
}; | ||
}); | ||
|
||
nodes = convertGeoCoords(nodes); | ||
|
||
// TODO: remove | ||
// eslint-disable-next-line | ||
console.log(nodes); | ||
|
||
return nodes; | ||
}; | ||
|
||
export default importTimetable; |
28 changes: 28 additions & 0 deletions
28
front/src/applications/operationalStudies/components/MacroEditor/types.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
// NGE DTO types, see: | ||
// https://github.com/SchweizerischeBundesbahnen/netzgrafik-editor-frontend/blob/main/src/app/data-structures/business.data.structures.ts | ||
|
||
export type Haltezeit = { | ||
haltezeit: number; | ||
no_halt: boolean; | ||
}; | ||
|
||
export type Node = { | ||
id: string; // TODO: in NGE this is a number | ||
/** Trigram */ | ||
betriebspunktName: string; | ||
fullName: string; | ||
positionX: number; | ||
positionY: number; | ||
ports: unknown[]; | ||
transitions: unknown[]; | ||
connections: unknown[]; | ||
resourceId: number; | ||
/** Number of tracks where train can stop */ | ||
perronkanten: number; | ||
/** Time needed to change train in minutes */ | ||
connectionTime: number; | ||
trainrunCategoryHaltezeiten: { [category: string]: Haltezeit }; | ||
symmetryAxis: number; | ||
warnings: unknown[]; | ||
labelIds: number[]; | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters