diff --git a/js/bullets.js b/js/bullets.js
index ea0e30a..713bd9e 100644
--- a/js/bullets.js
+++ b/js/bullets.js
@@ -71,7 +71,7 @@ const b = {
{
name: "fluoroantimonic acid",
description: "each bullet does extra chemical damage
instant damage, unaffected by momentum",
- have: false, //11
+ have: false, //1
effect: () => { //good with guns that fire many bullets at low speeds, minigun, drones, junk-bots, shotgun, superballs, wavebeam
b.modExtraDmg = 0.1
}
@@ -79,7 +79,7 @@ const b = {
{
name: "fracture analysis",
description: "5x physical damage to unaware enemies
unaware enemies don't have a health bar",
- have: false, //16
+ have: false, //2
effect: () => { // good with high damage guns that strike from a distance: rail gun, drones, flechettes, spores, grenade, vacuum bomb
b.modIsCrit = true;
}
@@ -87,7 +87,7 @@ const b = {
{
name: "kinetic bombardment",
description: "do extra damage from a distance
up to 50% increase at about 30 steps away",
- have: false, //17
+ have: false, //3
effect: () => { // good with annihilation, melee builds
b.isModFarAwayDmg = true; //used in mob.damage()
}
@@ -95,7 +95,7 @@ const b = {
{
name: "quasistatic equilibrium",
description: "do extra damage at low health
up to 50% increase when near death",
- have: false, //18
+ have: false, //4
effect: () => { // good with annihilation, melee builds
b.isModLowHealthDmg = true; //used in mob.damage()
}
@@ -103,7 +103,7 @@ const b = {
{
name: "auto-loading heuristics",
description: "your delay after firing is 15% shorter",
- have: false, //1
+ have: false, //5
effect: () => { //good for guns with extra ammo: needles, M80, rapid fire, flak, super balls
b.modFireRate = 0.85
}
@@ -111,7 +111,7 @@ const b = {
{
name: "desublimated ammunition",
description: "use 50% less ammo when crouching",
- have: false, //2
+ have: false, //6
effect: () => { //good with guns that have less ammo: one shot, grenades, missiles, super balls, spray
b.modNoAmmo = 1
}
@@ -119,7 +119,7 @@ const b = {
{
name: "Lorentzian topology",
description: "your bullets last 40% longer",
- have: false, //3
+ have: false, //7
effect: () => { //good with: drones, super balls, spore, missiles, wave beam(range), rapid fire(range), flak(range)
b.isModBulletsLastLonger = 1.40
}
@@ -127,7 +127,7 @@ const b = {
{
name: "zoospore vector",
description: "enemies can discharge spores on death
spores seek out enemies",
- have: false, //7
+ have: false, //8
effect: () => { //good late game maybe?
b.modSpores = 0.20;
}
@@ -135,7 +135,7 @@ const b = {
{
name: "ablative synthesis",
description: "rebuild your broken parts as drones
chance to occur after taking damage",
- have: false, //6
+ have: false, //9
effect: () => { //makes dangerous situations more survivable
b.isModDroneOnDamage = true;
}
@@ -143,15 +143,15 @@ const b = {
{
name: "annihilation",
description: "after touching enemies, they are annihilated
doesn't trigger health or energy transfer",
- have: false, //12
+ have: false, //10
effect: () => { //good with mods that heal: superconductive healing, entropy transfer
b.modAnnihilation = true
}
},
{
name: "anti-matter cores",
- description: "the radius of your explosions is doubled
be careful",
- have: false, //4
+ description: "the radius of your explosions is doubled
be careful",
+ have: false, //11
effect: () => { //at 1.4 gives a flat 40% increase, and increased range, balanced by limited guns and self damage
//testing at 1.3: grenade(+0.3), missiles, flak, M80
b.modExplosionRadius = 1.8; //good for guns with explosions
@@ -160,15 +160,79 @@ const b = {
{
name: "ceramic plating",
description: "protection from to high temperatures
5x less damage from explosions and lasers",
- have: false, //5
+ have: false, //12
effect: () => {
b.isModTempResist = true; //good for guns with explosions
}
},
{
- name: "Gauss rifle",
- description: "launch blocks at much higher speeds
hold onto larger blocks even after getting hit",
+ name: "entanglement",
+ description: "using your first gun reduces damage taken
scales by 7% for each gun in your inventory",
+ have: false, //13
+ effect: () => { // good with laser-bots
+ b.isModMonogamy = true
+ }
+ },
+ {
+ name: "energy transfer",
+ description: "gain energy proportional to damage done",
have: false, //14
+ effect: () => { //good with laser, and all fields
+ b.modEnergySiphon = 0.2;
+ }
+ },
+ {
+ name: "entropy transfer",
+ description: "heal proportional to damage done",
+ have: false, //15
+ effect: () => { //good with guns that overkill: one shot, grenade
+ b.modHealthDrain = 0.015;
+ }
+ },
+ {
+ name: "overcharge",
+ description: "charge energy 25% beyond your maximum",
+ have: false, //16
+ effect: () => {
+ mech.fieldEnergyMax = 1.25
+ }
+ },
+ {
+ name: "supersaturation",
+ description: "heal 25% beyond your max health",
+ have: false, //17
+ effect: () => {
+ mech.maxHealth = 1.25
+ }
+ },
+ {
+ name: "recursive healing",
+ description: "healing power ups bring you to max health",
+ have: false, //18
+ effect: () => { // good with ablative synthesis, melee builds
+ b.isModFullHeal = true
+ }
+ },
+ {
+ name: "mass-energy equivalence",
+ description: "convert the mass of power ups into energy
power ups fill your energy and heal for +3%",
+ have: false, //19
+ effect: () => {
+ b.isModMassEnergy = true // used in mech.usePowerUp
+ }
+ },
+ {
+ name: "Bayesian inference",
+ description: "20% chance for double power ups to drop",
+ have: false, //20
+ effect: () => { // good with long term planning
+ b.modMoreDrops = 0.20;
+ }
+ },
+ {
+ name: "Gauss rifle",
+ description: "launch blocks at much higher speeds
hold onto larger blocks even after getting hit",
+ have: false, //21
effect: () => { // good with guns that run out of ammo
mech.throwChargeRate = 4;
mech.throwChargeMax = 150;
@@ -178,73 +242,17 @@ const b = {
{
name: "squirrel-cage rotor",
description: "jump higher and move faster
reduced falling damage",
- have: false, //15
+ have: false, //22
effect: () => { // good with melee builds, content skipping builds
b.modSquirrelFx = 1.2;
mech.Fx = 0.015 * b.modSquirrelFx;
mech.jumpForce = 0.38 * 1.1;
}
},
- {
- name: "energy transfer",
- description: "gain energy proportional to damage done",
- have: false, //8
- effect: () => { //good with laser, and all fields
- b.modEnergySiphon = 0.2;
- }
- },
- {
- name: "entropy transfer",
- description: "heal proportional to damage done",
- have: false, //9
- effect: () => { //good with guns that overkill: one shot, grenade
- b.modHealthDrain = 0.015;
- }
- },
- {
- name: "entanglement",
- description: "using your first gun reduces damage taken
scales by 7% for each gun in your inventory",
- have: false, //20
- effect: () => { // good with laser-bots
- b.isModMonogamy = true
- }
- },
- {
- name: "Bayesian inference",
- description: "20% chance for double power ups to drop",
- have: false, //19
- effect: () => { // good with long term planning
- b.modMoreDrops = 0.20;
- }
- },
- {
- name: "mass-energy equivalence",
- description: "change the mass of power ups into energy
power ups fill your energy and heal for +3%",
- have: false, //21
- effect: () => {
- b.isModMassEnergy = true // used in mech.usePowerUp
- }
- },
- {
- name: "supersaturation",
- description: "heal 25% beyond your max health",
- have: false, //22
- effect: () => {
- mech.maxHealth = 1.25
- }
- },
- {
- name: "recursive healing",
- description: "healing power ups bring you to full health",
- have: false, //13
- effect: () => { // good with ablative synthesis, melee builds
- b.isModFullHeal = true
- }
- },
{
name: "quantum immortality",
- description: "after dying, continue in an alternate reality
guns, ammo, and field are randomized",
- have: false, //10
+ description: "after dying, continue in an alternate reality
guns, ammo, and field are randomized",
+ have: false, //23
effect: () => {
b.modIsImmortal = true;
}
@@ -301,18 +309,10 @@ const b = {
}
}
},
- draw() {
- ctx.beginPath();
+ bulletActions() {
+ //remove bullet if at end cycle for that bullet
let i = bullet.length;
while (i--) {
- //draw
- let vertices = bullet[i].vertices;
- ctx.moveTo(vertices[0].x, vertices[0].y);
- for (let j = 1; j < vertices.length; j += 1) {
- ctx.lineTo(vertices[j].x, vertices[j].y);
- }
- ctx.lineTo(vertices[0].x, vertices[0].y);
- //remove bullet if at end cycle for that bullet
if (bullet[i].endCycle < game.cycle) {
bullet[i].onEnd(i); //some bullets do stuff on end
if (bullet[i]) {
@@ -323,9 +323,21 @@ const b = {
}
}
}
+
+ //draw
+ ctx.beginPath();
+ for (let i = 0, len = bullet.length; i < len; i++) {
+ let vertices = bullet[i].vertices;
+ ctx.moveTo(vertices[0].x, vertices[0].y);
+ for (let j = 1; j < vertices.length; j += 1) {
+ ctx.lineTo(vertices[j].x, vertices[j].y);
+ }
+ ctx.lineTo(vertices[0].x, vertices[0].y);
+ }
ctx.fillStyle = "#000";
ctx.fill();
- //do things
+
+ //do bullet things
for (let i = 0, len = bullet.length; i < len; i++) {
bullet[i].do();
}
@@ -380,16 +392,6 @@ const b = {
ctx.arc(mech.pos.x + 35 * Math.cos(mech.angle), mech.pos.y + 35 * Math.sin(mech.angle), radius, 0, 2 * Math.PI);
ctx.fill();
},
- drawOneBullet(vertices) {
- ctx.beginPath();
- ctx.moveTo(vertices[0].x, vertices[0].y);
- for (let j = 1; j < vertices.length; j += 1) {
- ctx.lineTo(vertices[j].x, vertices[j].y);
- }
- ctx.lineTo(vertices[0].x, vertices[0].y);
- ctx.fillStyle = "#000";
- ctx.fill();
- },
removeConsBB(me) {
for (let i = 0, len = consBB.length; i < len; ++i) {
if (consBB[i].bodyA === me) {
@@ -567,7 +569,7 @@ const b = {
},
guns: [{
name: "laser", //0
- description: "emit a beam of damaging coherent light
uses energy instead of ammunition",
+ description: "emit a beam of collimation coherent light
uses energy instead of ammunition",
ammo: 0,
// ammoPack: 350,
ammoPack: Infinity,
@@ -1102,7 +1104,6 @@ const b = {
bullet[me] = Bodies.rectangle(mech.pos.x + 40 * Math.cos(dir), mech.pos.y + 40 * Math.sin(dir), 32 * size * b.modBulletSize, 0.8 * size * b.modBulletSize, b.fireAttributes(dir));
bullet[me].endCycle = game.cycle + Math.floor(180 * b.isModBulletsLastLonger);
bullet[me].dmg = 0.15 * size + b.modExtraDmg;
- b.drawOneBullet(bullet[me].vertices);
bullet[me].do = function () {
this.force.y += this.mass * 0.0002; //low gravity
};
@@ -1140,7 +1141,6 @@ const b = {
bullet[me] = Bodies.rectangle(mech.pos.x + 40 * Math.cos(mech.angle), mech.pos.y + 40 * Math.sin(mech.angle) - 3, 30 * b.modBulletSize, 4 * b.modBulletSize, b.fireAttributes(dir));
b.fireProps(mech.crouch ? 70 : 30, -3 * (0.5 - Math.random()) + (mech.crouch ? 25 : -8), dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
// Matter.Body.setDensity(bullet[me], 0.01) //doesn't help with reducing explosion knock backs
bullet[me].force.y += 0.00045; //a small push down at first to make it seem like the missile is briefly falling
bullet[me].frictionAir = 0
@@ -1284,7 +1284,6 @@ const b = {
const dir = mech.angle; // + Math.random() * 0.05;
bullet[me] = Bodies.circle(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 15 * b.modBulletSize, b.fireAttributes(dir, false));
b.fireProps(mech.crouch ? 40 : 20, mech.crouch ? 43 : 32, dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
// Matter.Body.setDensity(bullet[me], 0.000001);
bullet[me].totalCycles = 100;
bullet[me].endCycle = game.cycle + Math.floor((mech.crouch ? 120 : 60) * b.isModBulletsLastLonger);
@@ -1315,7 +1314,6 @@ const b = {
bullet[me].radius = 22; //used from drawing timer
b.fireProps(10, mech.crouch ? 42 : 26, dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
bullet[me].endCycle = Infinity
// bullet[me].restitution = 0.3;
// bullet[me].frictionAir = 0.01;
@@ -1423,7 +1421,6 @@ const b = {
const dir = mech.angle;
bullet[me] = Bodies.circle(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 15 * b.modBulletSize, b.fireAttributes(dir, false));
b.fireProps(mech.crouch ? 40 : 30, mech.crouch ? 34 : 22, dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
bullet[me].endCycle = game.cycle + Math.floor(60 * b.isModBulletsLastLonger);
bullet[me].restitution = 0.3;
// bullet[me].frictionAir = 0.01;
@@ -1494,7 +1491,6 @@ const b = {
const dir = mech.angle;
bullet[me] = Bodies.polygon(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 20, 4.5, b.fireAttributes(dir, false));
b.fireProps(mech.crouch ? 75 : 55, mech.crouch ? 25 : 14, dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
Matter.Body.setDensity(bullet[me], 0.000001);
bullet[me].endCycle = game.cycle + 100;
bullet[me].frictionAir = 0;
@@ -1687,7 +1683,6 @@ const b = {
}
})
b.fireProps(mech.crouch ? 14 : 10, mech.crouch ? 40 : 1, dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
}
},
{
@@ -1788,83 +1783,90 @@ const b = {
}
})
b.fireProps(mech.crouch ? 60 : 30, 15, dir, me); //cd , speed
- b.drawOneBullet(bullet[me].vertices);
}
},
{
- name: "chronon", //15
- description: "fire a bubble of null time
enemies are frozen for 5 seconds",
+ name: "foam", //15
+ description: "spray bubbly foam that sticks to enemies
does damage over time and slows movement",
ammo: 0,
ammoPack: 80,
have: false,
isStarterGun: true,
fire() {
const me = bullet.length;
- const dir = mech.angle
- const RADIUS = 23 + 45 * Math.random()
- bullet[me] = Bodies.polygon(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 0, RADIUS, {
- density: 0.0001, // 0.1 normal density to keep damage consistent
- frictionAir: 0,
- restitution: 0.3,
+ const dir = mech.angle + 0.1 * (Math.random() - 0.5)
+ const RADIUS = (9 + 12 * Math.random()) * b.modBulletSize
+ bullet[me] = Bodies.polygon(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 25, RADIUS, {
angle: dir,
- friction: 0,
+ density: 0.000001, // 0.001 is normal density
+ inertia: Infinity,
frictionAir: 0,
- dmg: 0.5 + b.modExtraDmg, //damage done in addition to the damage from momentum
+ friction: 0.2,
+ restitution: 0.2,
+ dmg: b.modExtraDmg, //damage done in addition to the damage from momentum
classType: "bullet",
collisionFilter: {
category: 0x000100,
- mask: 0x010011 //mask: 0x000101, //for self collision
+ mask: 0x010011
},
minDmgSpeed: 0,
endCycle: Infinity, //game.cycle + Math.floor(265 * b.isModBulletsLastLonger),
+ count: 0,
radius: RADIUS,
+ target: null,
onDmg(who) {
- this.endCycle = 0; //bullet ends cycle after doing damage // also triggers explosion
- if (!who.isSleeping) {
- const sleep = function (who) {
- if (who) {
- who.storeVelocity = who.velocity
- who.storeAngularVelocity = who.angularVelocity
- Matter.Sleeping.set(who, true)
- }
- };
- setTimeout(sleep, 1, who);
-
- const awake = function (who) {
- if (who) {
- Matter.Sleeping.set(who, false)
- if (who.storeVelocity) {
- Matter.Body.setVelocity(who, {
- x: who.storeVelocity.x,
- y: who.storeVelocity.y
- })
- Matter.Body.setAngularVelocity(who, who.storeAngularVelocity)
- }
- }
- };
- setTimeout(awake, 5000, who);
+ if (!this.target && who.alive) {
+ this.target = who;
+ this.collisionFilter.category = 0x000000;
}
},
onEnd() {},
do() {
- //shrink
- const SCALE = 0.994
- Matter.Body.scale(this, SCALE, SCALE);
- this.radius *= SCALE;
- if (this.radius < 5) this.endCycle = 0;
+ this.force.y += this.mass * 0.00005;
+ //draw white circle
ctx.beginPath()
- ctx.arc(this.position.x, this.position.y, this.radius - 2, 0, 2 * Math.PI);
+ ctx.arc(this.position.x, this.position.y, this.radius * 0.97 - 1.6, 0, 2 * Math.PI);
ctx.fillStyle = "#fff"
ctx.fill()
+
+
+ if (!mech.isBodiesAsleep) { //if time dilation isn't active
+
+ if (this.count < 17) {
+ this.count++
+ //grow
+ const SCALE = 1.1
+ Matter.Body.scale(this, SCALE, SCALE);
+ this.radius *= SCALE;
+ } else {
+ //shrink
+ const SCALE = 1 - 0.006 / b.isModBulletsLastLonger
+ Matter.Body.scale(this, SCALE, SCALE);
+ this.radius *= SCALE;
+ if (this.radius < 11) this.endCycle = 0;
+ }
+
+
+ if (this.target && this.target.alive) {
+ Matter.Body.setPosition(this, this.target.position)
+ Matter.Body.setVelocity(this.target, Matter.Vector.mult(this.target.velocity, 0.95))
+ Matter.Body.setAngularVelocity(this.target, this.target.angularVelocity * 0.96)
+ this.target.damage(b.dmgScale * 0.0035);
+ } else {
+ //look for a new target
+ this.target = null
+ this.collisionFilter.category = 0x000100;
+ }
+ }
}
});
World.add(engine.world, bullet[me]); //add bullet to world
- mech.fireCDcycle = mech.cycle + Math.floor((mech.crouch ? 13 : 7) * b.modFireRate); // cool down
- const SPEED = mech.crouch ? 9 : 5;
+ mech.fireCDcycle = mech.cycle + Math.floor((mech.crouch ? 15 : 3) * b.modFireRate); // cool down
+ const SPEED = mech.crouch ? 25 : 16 - RADIUS * 0.25;
Matter.Body.setVelocity(bullet[me], {
- x: mech.Vx / 2 + SPEED * Math.cos(dir),
- y: mech.Vy / 2 + SPEED * Math.sin(dir)
+ x: SPEED * Math.cos(dir),
+ y: SPEED * Math.sin(dir)
});
bullet[me].direction = Matter.Vector.perp(bullet[me].velocity)
}
@@ -2010,7 +2012,6 @@ const b = {
// })
// b.fireProps(mech.crouch ? 19 : 15, mech.crouch ? 45 : 30, dir, me); //cd , speed
- // b.drawOneBullet(bullet[me].vertices);
// //find mob targets
// let closeDist = Infinity;
diff --git a/js/game.js b/js/game.js
index c8c10cd..ff87e29 100644
--- a/js/game.js
+++ b/js/game.js
@@ -43,8 +43,9 @@ const game = {
mech.hold();
level.drawFills();
game.draw.drawMapPath();
- b.draw();
b.fire();
+ b.bulletActions();
+ mobs.healthBar();
game.drawCircle();
ctx.restore();
}
@@ -415,6 +416,8 @@ const game = {
b.activeGun = null;
b.setModDefaults(); //remove mods
game.updateModHUD();
+ mech.fieldEnergyMax = 1
+ mech.maxHealth = 1
mech.fieldUpgrades[0].effect(); //set to default field
game.paused = false;
build.isShowingBuilds = false
@@ -873,7 +876,7 @@ const game = {
for (let i = 0, len = body.length; i < len; ++i) {
let vertices = body[i].vertices;
ctx.moveTo(vertices[0].x, vertices[0].y);
- for (let j = 1; j < vertices.length; j += 1) {
+ for (let j = 1; j < vertices.length; j++) {
ctx.lineTo(vertices[j].x, vertices[j].y);
}
ctx.lineTo(vertices[0].x, vertices[0].y);
diff --git a/js/index.js b/js/index.js
index e83264b..2ee2cd1 100644
--- a/js/index.js
+++ b/js/index.js
@@ -187,17 +187,17 @@ document.getElementById("build-button").addEventListener("click", () => {
-