diff --git a/dist/img/modules/fuelcan.svg b/dist/img/modules/fuelcan.svg new file mode 100644 index 0000000..10161c3 --- /dev/null +++ b/dist/img/modules/fuelcan.svg @@ -0,0 +1,82 @@ + + + + + + + + + + + + image/svg+xml + + + + + + + + + + + diff --git a/js/assets.mjs b/js/assets.mjs index 02820a3..2aca54f 100644 --- a/js/assets.mjs +++ b/js/assets.mjs @@ -23,7 +23,8 @@ export const images = { }, connector: { xheavy: 'modules/xheavy_connector.svg' - } + }, + fuelcan: 'modules/fuelcan.svg' }, celestials: { green: { @@ -35,6 +36,7 @@ export const images = { export const audio = { itemPickup: 'up1.mp3', + fuelPickup: 'blip2.mp3', endEdit: 'release1.mp3' }; diff --git a/js/consts.mjs b/js/consts.mjs index 9f4c718..975ae1d 100644 --- a/js/consts.mjs +++ b/js/consts.mjs @@ -23,7 +23,7 @@ export const ZOOM_SPEED = 0.01; export const TIP_ANGLE = 0.25; export const TIP_SPEED = 0.03; // Ship flight mechanics. Speed measured in units per tick. -export const FUEL_BURN_RATE = 0.01; +export const FUEL_BURN_RATE = 0.3; export const THRUST_POWER = 0.004; export const TURN_POWER = 0.07; // Distance at which an orbited planet will not be considered a parent body. @@ -33,6 +33,7 @@ export const EDIT_MARGIN = 2; // Floating items. export const ENTITY_ROTATION_RATE = 0.01; // World generation. -export const PLANET_SPAWN_RATE = 0.00002; -export const ENTITY_SPAWN_RATE = 0.3; +export const PLANET_SPAWN_RATE = 3; +export const ENTITY_SPAWN_RATE = 8; export const MIN_CELESTIAL_SPACING = 15; +export const FUEL_CAN_AMOUNT = 4; diff --git a/js/game/events.mjs b/js/game/events.mjs index 9c69b82..1269c16 100644 --- a/js/game/events.mjs +++ b/js/game/events.mjs @@ -5,6 +5,7 @@ import * as inventory from './inventory.mjs'; import * as particle from '../world/particle.mjs'; import * as edit from './edit.mjs'; import * as audio from './audio.mjs'; +import * as consts from '../consts.mjs'; export let shipLanded = false; export let score = 0; @@ -105,9 +106,17 @@ export function tossItem() { } export function collectItem(type, id) { - inventory.addItem(type, id); - audio.play('itemPickup'); - score += 20; - notify('Collected module: +20'); - return true; + if (type === 'fuelcan') { + world.playerShip.addFuel(consts.FUEL_CAN_AMOUNT); + audio.play('fuelPickup'); + score += 10; + notify('Collected fuel: +10'); + return true; + } else { + inventory.addItem(type, id); + audio.play('itemPickup'); + score += 20; + notify('Collected module: +20'); + return true; + } } diff --git a/js/world/body.mjs b/js/world/body.mjs index a575adf..569f11c 100644 --- a/js/world/body.mjs +++ b/js/world/body.mjs @@ -110,13 +110,13 @@ export default class Body { this.rvel += r / this.mass; } - orbit(cel, altitude) { + orbit(cel, altitude, angle = 0) { this.gravity = true; let speed = Math.sqrt(G * cel.mass / (altitude + cel.radius)); let [cx, cy] = cel.com; - this.x = cx; - this.y = cy - (altitude + cel.radius); - this.yvel = 0; - this.xvel = speed; + let [dx, dy] = this.rotateVector(0, -(altitude + cel.radius), angle); + [this.xvel, this.yvel] = this.rotateVector(speed, 0, angle); + this.x = cx + dx; + this.y = cy + dy; } } diff --git a/js/world/entity.mjs b/js/world/entity.mjs index 1fa448d..5bc9ff0 100644 --- a/js/world/entity.mjs +++ b/js/world/entity.mjs @@ -14,7 +14,6 @@ export default class Entity extends Body { gravity = false } = {}) { super(x, y, 0.1); - this.xvel = xvel; this.yvel = yvel; this.width = 1; @@ -22,7 +21,13 @@ export default class Entity extends Body { this.radius = (this.width + this.height) / 2; this.type = type; this.id = id; - this.image = assets.modules[type][id]; + if (this.type === 'fuelcan') { + this.image = assets.modules.fuelcan; + } else { + this.image = assets.modules[type][id]; + if (this.type === 'thruster') + this.image = this.image.off; + } this.gravity = gravity; this.touched = false; } @@ -36,6 +41,8 @@ export default class Entity extends Body { } tick() { + if (Math.abs(playerShip.x - this.x) > 500 || + Math.abs(playerShip.y - this.y) > 500) return; this.r += consts.ENTITY_ROTATION_RATE; this.tickMotion(); if (this.gravity) this.tickGravity(celestials); @@ -47,6 +54,7 @@ export default class Entity extends Body { if (playerShip.colliding(this.com, this.radius)) { if (this.touched) return; + this.touched = true; let success = events.collectItem(this.type, this.id); if (!success) return; particle.createPickupBurst(playerShip, this.com); diff --git a/js/world/module.mjs b/js/world/module.mjs index f5b4b4b..6c6fe3e 100644 --- a/js/world/module.mjs +++ b/js/world/module.mjs @@ -7,8 +7,6 @@ export default class Module { type = 'block', id = 'unknown', mass = 1, - // Fuel - filled = false, fuelCapacity = 0, ...properties }) { @@ -21,10 +19,8 @@ export default class Module { this.id = id; this.images = assets.modules[this.type][this.id]; this.data = modules[this.type][this.id]; - // Fuel - if (this.type == 'fuel') { - this.fuel = filled ? fuelCapacity : 0; - } else if (this.type == 'thruster') { + + if (this.type == 'thruster') { this.power = 0; } } diff --git a/js/world/ship.mjs b/js/world/ship.mjs index a9982d1..4ad831a 100644 --- a/js/world/ship.mjs +++ b/js/world/ship.mjs @@ -74,6 +74,10 @@ export default class Ship extends Body { this.modules.clear(); } + addFuel(amount) { + this.fuel = Math.min(this.fuel + amount, this.maxFuel); + } + addModule(x, y, properties, options) { let module = new Module(x, y, this, {...properties, ...options}); this.modules.add(module); @@ -188,6 +192,7 @@ export default class Ship extends Body { let thrustForce = -forward * consts.THRUST_POWER * this.thrust; let turnForce = (turnRight - turnLeft) * consts.TURN_POWER; turnForce *= this.rotationPower; + this.fuel -= Math.abs(thrustForce) * consts.FUEL_BURN_RATE; this.applyDirectionalForce(0, thrustForce, turnForce); diff --git a/js/world/spawn.mjs b/js/world/spawn.mjs index b900ead..56e8bfa 100644 --- a/js/world/spawn.mjs +++ b/js/world/spawn.mjs @@ -41,11 +41,11 @@ function nearest(x, y, set) { function spawnSector(x, y) { let area = SS ** 2; - for (let i = 0; i < area / 10000; i++) { + for (let i = 0; i < area / 1000; i++) { let [px, py] = [(x + Math.random()) * SS, (y + Math.random()) * SS]; - if (Math.random() > consts.PLANET_SPAWN_RATE) { + if (Math.random() < consts.PLANET_SPAWN_RATE / 1000) { randomPlanet(px, py); - } else if (Math.random() > 0.01 ){ + } else if (Math.random() < consts.ENTITY_SPAWN_RATE / 1000){ randomEntity(px, py); } } @@ -68,13 +68,23 @@ function randomPlanet(x, y) { for (let i = 1.5; i < 8; i += 1) { if (Math.random() > consts.ENTITY_SPAWN_RATE) { let e = randomEntity(); - e.orbit(planet, i * rad); + e.orbit(planet, i * rad, Math.random() * Math.PI * 2); } } } function randomEntity(x, y) { - let entity = new Entity(x, y); + let entity, type, id; + + if (Math.random() > 0.3) { + entity = new Entity(x, y, 'fuelcan'); + } else { + let arr = Object.entries(modules); + [type, arr] = arr[Math.random() * arr.length | 0]; + arr = Object.keys(arr); + entity = new Entity(x, y, type, arr[Math.random() * arr.length | 0]); + } + world.entities.add(entity); return entity; } @@ -88,6 +98,7 @@ export function player() { //ship.addModule(-1, 2, modules.thruster.light); world.ships.add(ship); world.setPlayerShip(ship); + ship.addFuel(ship.maxFuel); let tracer = new Tracer(ship); world.tracers.add(tracer);