234 lines
7.8 KiB
JavaScript
234 lines
7.8 KiB
JavaScript
// Input Handling
|
|
const Input = {
|
|
currentTool: 'select',
|
|
rotation: 0,
|
|
mouseScreen: { x: 0, y: 0 },
|
|
mouseWorld: { x: 0, y: 0 },
|
|
isDragging: false,
|
|
lastMouse: { x: 0, y: 0 },
|
|
isMouseDown: false,
|
|
|
|
// Initialize input handlers
|
|
init() {
|
|
const canvas = Renderer.canvas;
|
|
|
|
canvas.addEventListener('mousedown', (e) => this.onMouseDown(e));
|
|
canvas.addEventListener('mousemove', (e) => this.onMouseMove(e));
|
|
canvas.addEventListener('mouseup', (e) => this.onMouseUp(e));
|
|
canvas.addEventListener('mouseleave', () => this.onMouseLeave());
|
|
canvas.addEventListener('wheel', (e) => this.onWheel(e));
|
|
canvas.addEventListener('contextmenu', (e) => e.preventDefault());
|
|
document.addEventListener('keydown', (e) => this.onKeyDown(e));
|
|
},
|
|
|
|
// Mouse down handler
|
|
onMouseDown(e) {
|
|
const rect = Renderer.canvas.getBoundingClientRect();
|
|
const mx = e.clientX - rect.left;
|
|
const my = e.clientY - rect.top;
|
|
|
|
// Right click or middle click to drag
|
|
if (e.button === 2 || e.button === 1) {
|
|
this.isDragging = true;
|
|
this.lastMouse = { x: e.clientX, y: e.clientY };
|
|
Renderer.canvas.style.cursor = 'grabbing';
|
|
return;
|
|
}
|
|
|
|
this.isMouseDown = true;
|
|
const world = Utils.screenToWorld(mx, my, Renderer.camera);
|
|
|
|
if (this.currentTool === 'select') {
|
|
const building = Buildings.getAt(world.x, world.y);
|
|
if (building && building.type === 'assembler') {
|
|
game.ui.showRecipeSelect(e.clientX, e.clientY, building);
|
|
}
|
|
} else if (this.currentTool === 'delete') {
|
|
Buildings.remove(world.x, world.y);
|
|
Towers.remove(world.x, world.y);
|
|
} else if (this.currentTool === 'mine') {
|
|
// Start manual mining
|
|
Simulation.startMining(world.x, world.y);
|
|
} else if (Towers.TYPES[this.currentTool]) {
|
|
// Place tower
|
|
Towers.place(this.currentTool, world.x, world.y);
|
|
} else {
|
|
Buildings.place(this.currentTool, world.x, world.y, this.rotation);
|
|
}
|
|
},
|
|
|
|
// Mouse move handler
|
|
onMouseMove(e) {
|
|
const rect = Renderer.canvas.getBoundingClientRect();
|
|
this.mouseScreen.x = e.clientX - rect.left;
|
|
this.mouseScreen.y = e.clientY - rect.top;
|
|
this.mouseWorld = Utils.screenToWorld(this.mouseScreen.x, this.mouseScreen.y, Renderer.camera);
|
|
|
|
if (this.isDragging) {
|
|
Renderer.camera.x -= (e.clientX - this.lastMouse.x);
|
|
Renderer.camera.y -= (e.clientY - this.lastMouse.y);
|
|
this.lastMouse = { x: e.clientX, y: e.clientY };
|
|
return;
|
|
}
|
|
|
|
// Continue mining if holding mouse and using mine tool
|
|
if (this.isMouseDown && this.currentTool === 'mine') {
|
|
if (!Simulation.mining.active ||
|
|
Simulation.mining.x !== this.mouseWorld.x ||
|
|
Simulation.mining.y !== this.mouseWorld.y) {
|
|
Simulation.startMining(this.mouseWorld.x, this.mouseWorld.y);
|
|
}
|
|
}
|
|
|
|
// Update tooltip
|
|
game.ui.updateTooltip(e.clientX, e.clientY, this.mouseWorld);
|
|
},
|
|
|
|
// Mouse up handler
|
|
onMouseUp(e) {
|
|
this.isDragging = false;
|
|
this.isMouseDown = false;
|
|
Renderer.canvas.style.cursor = 'crosshair';
|
|
|
|
// Stop mining when releasing mouse
|
|
if (this.currentTool === 'mine') {
|
|
Simulation.stopMining();
|
|
}
|
|
},
|
|
|
|
// Mouse leave handler
|
|
onMouseLeave() {
|
|
this.isDragging = false;
|
|
this.isMouseDown = false;
|
|
if (this.currentTool === 'mine') {
|
|
Simulation.stopMining();
|
|
}
|
|
},
|
|
|
|
// Mouse wheel handler
|
|
onWheel(e) {
|
|
e.preventDefault();
|
|
const oldZoom = Renderer.camera.zoom;
|
|
const zoomFactor = e.deltaY > 0 ? 0.9 : 1.1;
|
|
Renderer.camera.zoom = Utils.clamp(Renderer.camera.zoom * zoomFactor, 0.4, 2.5);
|
|
|
|
// Zoom toward mouse position
|
|
const worldX = (this.mouseScreen.x + Renderer.camera.x) / oldZoom;
|
|
const worldY = (this.mouseScreen.y + Renderer.camera.y) / oldZoom;
|
|
Renderer.camera.x = worldX * Renderer.camera.zoom - this.mouseScreen.x;
|
|
Renderer.camera.y = worldY * Renderer.camera.zoom - this.mouseScreen.y;
|
|
},
|
|
|
|
// Key down handler
|
|
onKeyDown(e) {
|
|
const key = e.key.toLowerCase();
|
|
|
|
switch (key) {
|
|
case 'r':
|
|
this.rotation = (this.rotation + 1) % 4;
|
|
break;
|
|
case 'q':
|
|
this.selectTool('select');
|
|
break;
|
|
case 'x':
|
|
this.selectTool('delete');
|
|
break;
|
|
case 'e':
|
|
this.selectTool('mine');
|
|
break;
|
|
case '1':
|
|
this.selectTool('miner');
|
|
break;
|
|
case '2':
|
|
this.selectTool('belt');
|
|
break;
|
|
case '3':
|
|
this.selectTool('inserter');
|
|
break;
|
|
case '4':
|
|
this.selectTool('chest');
|
|
break;
|
|
case '5':
|
|
this.selectTool('furnace');
|
|
break;
|
|
case '6':
|
|
this.selectTool('assembler');
|
|
break;
|
|
case '7':
|
|
this.selectTool('gun_turret');
|
|
break;
|
|
case '8':
|
|
this.selectTool('flame_turret');
|
|
break;
|
|
case '9':
|
|
this.selectTool('laser_turret');
|
|
break;
|
|
case '0':
|
|
this.selectTool('tesla_turret');
|
|
break;
|
|
case '-':
|
|
this.selectTool('cannon_turret');
|
|
break;
|
|
case '`':
|
|
case '~':
|
|
// Toggle dev mode
|
|
CONFIG.DEV_MODE = !CONFIG.DEV_MODE;
|
|
game.ui.showDevModeNotification();
|
|
Audio.playDevMode();
|
|
break;
|
|
case 'f1':
|
|
// Dev: Spawn wave immediately
|
|
if (CONFIG.DEV_MODE) {
|
|
e.preventDefault();
|
|
Enemies.waveTimer = 0;
|
|
}
|
|
break;
|
|
case 'f2':
|
|
// Dev: Kill all enemies
|
|
if (CONFIG.DEV_MODE) {
|
|
e.preventDefault();
|
|
Enemies.list = [];
|
|
Enemies.enemiesRemaining = 0;
|
|
Enemies.spawnQueue = [];
|
|
}
|
|
break;
|
|
case 'f3':
|
|
// Dev: Add resources
|
|
if (CONFIG.DEV_MODE) {
|
|
e.preventDefault();
|
|
Resources.add('iron', 100);
|
|
Resources.add('copper', 100);
|
|
Resources.add('coal', 100);
|
|
Resources.add('iron-plate', 100);
|
|
Resources.add('copper-plate', 100);
|
|
Resources.add('gear', 50);
|
|
Resources.add('circuit', 50);
|
|
}
|
|
break;
|
|
case 'w':
|
|
case 'arrowup':
|
|
Renderer.camera.y -= 50;
|
|
break;
|
|
case 's':
|
|
case 'arrowdown':
|
|
Renderer.camera.y += 50;
|
|
break;
|
|
case 'a':
|
|
case 'arrowleft':
|
|
Renderer.camera.x -= 50;
|
|
break;
|
|
case 'd':
|
|
case 'arrowright':
|
|
Renderer.camera.x += 50;
|
|
break;
|
|
}
|
|
},
|
|
|
|
// Select a tool
|
|
selectTool(tool) {
|
|
this.currentTool = tool;
|
|
Simulation.stopMining();
|
|
game.ui.updateToolButtons(tool);
|
|
}
|
|
};
|