Add mass driver station system with Lagrange point placement
- Lagrange point computation (L1-L5) for any Sun-planet pair in Rust - Station generation: auto-place at Lagrange points by priority (inner → outer planets) - Station panel UI: count slider (5-50), launch velocity slider (5-100 km/s) with info tooltip - Blue diamond markers on 2D canvas with labels when zoomed in - Active station list in sidebar (Earth L1, Mars L2, Jupiter L4, etc.) - WASM API: generate_stations(), get_station_positions(), get_station_names() - Station positions update every frame (co-rotating with planets at Lagrange points) Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -17,6 +17,9 @@ export class SolarSystem2DRenderer {
|
||||
private positions: Float64Array = new Float64Array(0);
|
||||
private velocities: Float64Array = new Float64Array(0);
|
||||
private orbitPoints: Map<number, Float64Array> = new Map();
|
||||
private stationPositions: Float64Array = new Float64Array(0);
|
||||
private stationNames: string[] = [];
|
||||
private showStations: boolean = true;
|
||||
private isDragging = false;
|
||||
private lastMouse = { x: 0, y: 0 };
|
||||
private animFrameId: number = 0;
|
||||
@@ -77,6 +80,12 @@ export class SolarSystem2DRenderer {
|
||||
this.orbitPoints.set(bodyId, points);
|
||||
}
|
||||
|
||||
updateStations(positions: Float64Array, names: string[], visible: boolean) {
|
||||
this.stationPositions = positions;
|
||||
this.stationNames = names;
|
||||
this.showStations = visible;
|
||||
}
|
||||
|
||||
render() {
|
||||
const { canvas, ctx } = this;
|
||||
const dpr = window.devicePixelRatio || 1;
|
||||
@@ -115,6 +124,15 @@ export class SolarSystem2DRenderer {
|
||||
}
|
||||
}
|
||||
|
||||
// Draw stations
|
||||
if (this.showStations && this.stationPositions.length > 0) {
|
||||
for (let i = 0; i < this.stationNames.length; i++) {
|
||||
const x = this.stationPositions[i * 3];
|
||||
const y = this.stationPositions[i * 3 + 1];
|
||||
this.drawStation(x, y, this.stationNames[i]);
|
||||
}
|
||||
}
|
||||
|
||||
// Scale indicator
|
||||
this.drawScaleBar(rect.width, rect.height);
|
||||
}
|
||||
@@ -269,6 +287,32 @@ export class SolarSystem2DRenderer {
|
||||
ctx.fillText(info.name, sx + size + 4, sy + 3);
|
||||
}
|
||||
|
||||
private drawStation(xAU: number, yAU: number, name: string) {
|
||||
const ctx = this.ctx;
|
||||
const [sx, sy] = this.auToScreen(xAU, yAU);
|
||||
|
||||
// Diamond shape
|
||||
const s = 3;
|
||||
ctx.fillStyle = 'rgba(74, 158, 255, 0.6)';
|
||||
ctx.strokeStyle = 'rgba(74, 158, 255, 0.8)';
|
||||
ctx.lineWidth = 1;
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(sx, sy - s);
|
||||
ctx.lineTo(sx + s, sy);
|
||||
ctx.lineTo(sx, sy + s);
|
||||
ctx.lineTo(sx - s, sy);
|
||||
ctx.closePath();
|
||||
ctx.fill();
|
||||
ctx.stroke();
|
||||
|
||||
// Label (only show when zoomed in enough)
|
||||
if (this.getScale() > 50) {
|
||||
ctx.fillStyle = 'rgba(74, 158, 255, 0.5)';
|
||||
ctx.font = '8px monospace';
|
||||
ctx.fillText(name, sx + s + 3, sy + 3);
|
||||
}
|
||||
}
|
||||
|
||||
private drawScaleBar(w: number, h: number) {
|
||||
const ctx = this.ctx;
|
||||
const scale = this.getScale();
|
||||
|
||||
Reference in New Issue
Block a user