vaccum bomb grenade mod
gun: vacuum bomb is removed
mod: vacuum bomb - grenades fire slower, explode bigger and, suck everything towards them
laser and diffuse laser graphics are better
mod: output coupler - diffuse laser beam is 30% wider and does 30% more damage
requires diffuse beam
level number doesn't increase if you skip the boss (in the late game)
This commit is contained in:
@@ -132,7 +132,7 @@
|
|||||||
</div>
|
</div>
|
||||||
</details>
|
</details>
|
||||||
</div>
|
</div>
|
||||||
<div id="controls">
|
<div>
|
||||||
<details id="control-details">
|
<details id="control-details">
|
||||||
<summary>controls</summary>
|
<summary>controls</summary>
|
||||||
<div id="details-div">
|
<div id="details-div">
|
||||||
@@ -196,7 +196,7 @@
|
|||||||
</div>
|
</div>
|
||||||
</details>
|
</details>
|
||||||
</div>
|
</div>
|
||||||
<div id="controls">
|
<div>
|
||||||
<details>
|
<details>
|
||||||
<summary>about</summary>
|
<summary>about</summary>
|
||||||
<div id="details-div">
|
<div id="details-div">
|
||||||
|
|||||||
218
js/bullet.js
218
js/bullet.js
@@ -461,11 +461,18 @@ const b = {
|
|||||||
if (best.who.alive) {
|
if (best.who.alive) {
|
||||||
best.who.damage(damage);
|
best.who.damage(damage);
|
||||||
best.who.locatePlayer();
|
best.who.locatePlayer();
|
||||||
ctx.fillStyle = color; //draw mob damage circle
|
game.drawList.push({ //add dmg to draw queue
|
||||||
ctx.beginPath();
|
x: path[path.length - 1].x,
|
||||||
ctx.arc(path[path.length - 1].x, path[path.length - 1].y, Math.sqrt(damage) * 100, 0, 2 * Math.PI);
|
y: path[path.length - 1].y,
|
||||||
ctx.fill();
|
radius: Math.sqrt(damage) * 100,
|
||||||
|
color: "rgba(255,0,0,0.5)",
|
||||||
|
time: game.drawTime
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
// ctx.fillStyle = color; //draw mob damage circle
|
||||||
|
// ctx.beginPath();
|
||||||
|
// ctx.arc(path[path.length - 1].x, path[path.length - 1].y, Math.sqrt(damage) * 100, 0, 2 * Math.PI);
|
||||||
|
// ctx.fill();
|
||||||
};
|
};
|
||||||
const reflection = function () { // https://math.stackexchange.com/questions/13261/how-to-get-a-reflection-vector
|
const reflection = function () { // https://math.stackexchange.com/questions/13261/how-to-get-a-reflection-vector
|
||||||
const n = Vector.perp(Vector.normalise(Vector.sub(best.v1, best.v2)));
|
const n = Vector.perp(Vector.normalise(Vector.sub(best.v1, best.v2)));
|
||||||
@@ -510,16 +517,10 @@ const b = {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (isThickBeam) {
|
if (isThickBeam) {
|
||||||
ctx.strokeStyle = color;
|
|
||||||
ctx.lineWidth = 8
|
|
||||||
ctx.globalAlpha = 0.5;
|
|
||||||
for (let i = 1, len = path.length; i < len; ++i) {
|
for (let i = 1, len = path.length; i < len; ++i) {
|
||||||
ctx.beginPath();
|
|
||||||
ctx.moveTo(path[i - 1].x, path[i - 1].y);
|
ctx.moveTo(path[i - 1].x, path[i - 1].y);
|
||||||
ctx.lineTo(path[i].x, path[i].y);
|
ctx.lineTo(path[i].x, path[i].y);
|
||||||
ctx.stroke();
|
|
||||||
}
|
}
|
||||||
ctx.globalAlpha = 1;
|
|
||||||
} else {
|
} else {
|
||||||
ctx.strokeStyle = color;
|
ctx.strokeStyle = color;
|
||||||
ctx.lineWidth = 2
|
ctx.lineWidth = 2
|
||||||
@@ -804,9 +805,13 @@ const b = {
|
|||||||
mobs.statusSlow(who, 60)
|
mobs.statusSlow(who, 60)
|
||||||
this.endCycle = game.cycle
|
this.endCycle = game.cycle
|
||||||
if (mod.isHeavyWater) mobs.statusDoT(who, 0.15, 300)
|
if (mod.isHeavyWater) mobs.statusDoT(who, 0.15, 300)
|
||||||
if (mod.iceEnergy && !who.shield && !who.isShielded && who.dropPowerUp && !who.alive) {
|
if (mod.iceEnergy && !who.shield && !who.isShielded && who.dropPowerUp && who.alive) {
|
||||||
mech.energy += mod.iceEnergy * 0.66 * mech.maxEnergy
|
setTimeout(function () {
|
||||||
mech.addHealth(mod.iceEnergy * 0.04)
|
if (!who.alive) {
|
||||||
|
mech.energy += mod.iceEnergy * 0.66 * mech.maxEnergy
|
||||||
|
mech.addHealth(mod.iceEnergy * 0.04)
|
||||||
|
}
|
||||||
|
}, 10);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onEnd() {},
|
onEnd() {},
|
||||||
@@ -2330,6 +2335,9 @@ const b = {
|
|||||||
ammoPack: 5,
|
ammoPack: 5,
|
||||||
have: false,
|
have: false,
|
||||||
fire() {
|
fire() {
|
||||||
|
|
||||||
|
},
|
||||||
|
fireNormal() {
|
||||||
const me = bullet.length;
|
const me = bullet.length;
|
||||||
const dir = mech.angle; // + Math.random() * 0.05;
|
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), 20, b.fireAttributes(dir, false));
|
bullet[me] = Bodies.circle(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 20, b.fireAttributes(dir, false));
|
||||||
@@ -2343,7 +2351,6 @@ const b = {
|
|||||||
bullet[me].beforeDmg = function () {
|
bullet[me].beforeDmg = function () {
|
||||||
this.endCycle = 0; //bullet ends cycle after doing damage //this also triggers explosion
|
this.endCycle = 0; //bullet ends cycle after doing damage //this also triggers explosion
|
||||||
};
|
};
|
||||||
|
|
||||||
if (mod.isRPG) {
|
if (mod.isRPG) {
|
||||||
b.fireProps(35, mech.crouch ? 60 : -15, dir, me); //cd , speed
|
b.fireProps(35, mech.crouch ? 60 : -15, dir, me); //cd , speed
|
||||||
bullet[me].endCycle = game.cycle + 70;
|
bullet[me].endCycle = game.cycle + 70;
|
||||||
@@ -2364,133 +2371,73 @@ const b = {
|
|||||||
b.fireProps(mech.crouch ? 40 : 30, mech.crouch ? 43 : 32, dir, me); //cd , speed
|
b.fireProps(mech.crouch ? 40 : 30, mech.crouch ? 43 : 32, dir, me); //cd , speed
|
||||||
bullet[me].endCycle = game.cycle + Math.floor(mech.crouch ? 120 : 80);
|
bullet[me].endCycle = game.cycle + Math.floor(mech.crouch ? 120 : 80);
|
||||||
bullet[me].restitution = 0.4;
|
bullet[me].restitution = 0.4;
|
||||||
bullet[me].explodeRad = 275;
|
|
||||||
bullet[me].do = function () {
|
bullet[me].do = function () {
|
||||||
//extra gravity for harder arcs
|
this.force.y += this.mass * 0.0025; //extra gravity for harder arcs
|
||||||
this.force.y += this.mass * 0.0025;
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
fireVacuum() {
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "vacuum bomb",
|
|
||||||
description: "fire a bomb that <strong>sucks</strong> before <strong class='color-e'>exploding</strong><br><strong>click</strong> left mouse again to <strong>detonate</strong>",
|
|
||||||
ammo: 0,
|
|
||||||
ammoPack: 2,
|
|
||||||
have: false,
|
|
||||||
fire() {
|
|
||||||
const me = bullet.length;
|
const me = bullet.length;
|
||||||
const dir = mech.angle;
|
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), 35, b.fireAttributes(dir, false));
|
bullet[me] = Bodies.circle(mech.pos.x + 30 * Math.cos(mech.angle), mech.pos.y + 30 * Math.sin(mech.angle), 20, b.fireAttributes(dir, false));
|
||||||
b.fireProps(10, mech.crouch ? 42 : 28, dir, me); //cd , speed
|
Matter.Body.setDensity(bullet[me], 0.0003);
|
||||||
|
bullet[me].explodeRad = 400 + Math.floor(Math.random() * 50);;
|
||||||
Matter.Body.setDensity(bullet[me], 0.0002);
|
|
||||||
bullet[me].restitution = 0.2;
|
|
||||||
bullet[me].friction = 0.3;
|
|
||||||
bullet[me].endCycle = Infinity
|
|
||||||
bullet[me].explodeRad = 450 + Math.floor(Math.random() * 50);
|
|
||||||
bullet[me].onEnd = function () {
|
bullet[me].onEnd = function () {
|
||||||
b.explosion(this.position, this.explodeRad); //makes bullet do explosive damage at end
|
b.explosion(this.position, this.explodeRad); //makes bullet do explosive damage at end
|
||||||
|
if (mod.grenadeFragments) b.targetedNail(this.position, mod.grenadeFragments)
|
||||||
//also damage all mobs
|
|
||||||
if (mod.isVacuumShield) {
|
|
||||||
for (let i = 0, len = mob.length; i < len; ++i) {
|
|
||||||
if (mob[i].shield) {
|
|
||||||
const dist = Vector.magnitude(Vector.sub(this.position, mob[i].position)) - mob[i].radius;
|
|
||||||
if (dist < this.explodeRad) mob[i].health *= 0.2
|
|
||||||
}
|
|
||||||
}
|
|
||||||
const dist = Vector.magnitude(Vector.sub(this.position, player.position))
|
|
||||||
if (dist < this.explodeRad) mech.energy = 0 //remove player energy
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
bullet[me].beforeDmg = function () {
|
bullet[me].beforeDmg = function () {};
|
||||||
// this.endCycle = 0; //bullet ends cycle after doing damage //this triggers explosion
|
const cd = mech.crouch ? 90 : 75
|
||||||
};
|
b.fireProps(cd, mech.crouch ? 46 : 35, dir, me); //cd , speed
|
||||||
bullet[me].radius = 22; //used from drawing timer
|
bullet[me].endCycle = game.cycle + cd;
|
||||||
bullet[me].isArmed = false;
|
bullet[me].restitution = 0.4;
|
||||||
bullet[me].isSucking = false;
|
|
||||||
bullet[me].do = function () {
|
bullet[me].do = function () {
|
||||||
//extra gravity for harder arcs
|
this.force.y += this.mass * 0.0025; //extra gravity for harder arcs
|
||||||
this.force.y += this.mass * 0.0022;
|
|
||||||
|
|
||||||
//set armed and sucking status
|
const suckCycles = 40
|
||||||
if (!this.isArmed && !input.fire) {
|
if (game.cycle > this.endCycle - suckCycles) { //suck
|
||||||
this.isArmed = true
|
const that = this
|
||||||
} else if (this.isArmed && input.fire && !this.isSucking) {
|
|
||||||
this.isSucking = true;
|
|
||||||
this.endCycle = game.cycle + 50;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.isSucking) {
|
function suck(who, radius = that.explodeRad * 3.2) {
|
||||||
if (!mech.isBodiesAsleep) {
|
for (i = 0, len = who.length; i < len; i++) {
|
||||||
const that = this
|
const sub = Vector.sub(that.position, who[i].position);
|
||||||
let mag = 0.1
|
const dist = Vector.magnitude(sub);
|
||||||
|
if (dist < radius && dist > 150) {
|
||||||
function suck(who, radius = that.explodeRad * 3.5) {
|
knock = Vector.mult(Vector.normalise(sub), mag * who[i].mass / Math.sqrt(dist));
|
||||||
for (i = 0, len = who.length; i < len; i++) {
|
who[i].force.x += knock.x;
|
||||||
const sub = Vector.sub(that.position, who[i].position);
|
who[i].force.y += knock.y;
|
||||||
const dist = Vector.magnitude(sub);
|
|
||||||
if (dist < radius && dist > 150) {
|
|
||||||
knock = Vector.mult(Vector.normalise(sub), mag * who[i].mass / Math.sqrt(dist));
|
|
||||||
who[i].force.x += knock.x;
|
|
||||||
who[i].force.y += knock.y;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (game.cycle > this.endCycle - 5) {
|
|
||||||
mag = -0.22
|
|
||||||
suck(mob, this.explodeRad * 3)
|
|
||||||
suck(body, this.explodeRad * 2)
|
|
||||||
suck(powerUp, this.explodeRad * 1.5)
|
|
||||||
suck(bullet, this.explodeRad * 1.5)
|
|
||||||
suck([player], this.explodeRad * 1.3)
|
|
||||||
} else {
|
|
||||||
mag = 0.1
|
|
||||||
suck(mob, this.explodeRad * 3)
|
|
||||||
suck(body, this.explodeRad * 2)
|
|
||||||
suck(powerUp, this.explodeRad * 1.5)
|
|
||||||
suck(bullet, this.explodeRad * 1.5)
|
|
||||||
suck([player], this.explodeRad * 1.3)
|
|
||||||
}
|
|
||||||
//keep bomb in place
|
|
||||||
Matter.Body.setVelocity(this, {
|
|
||||||
x: 0,
|
|
||||||
y: 0
|
|
||||||
});
|
|
||||||
//draw suck
|
|
||||||
const radius = 3 * this.explodeRad * (this.endCycle - game.cycle) / 50
|
|
||||||
ctx.fillStyle = "rgba(0,0,0,0.1)";
|
|
||||||
ctx.beginPath();
|
|
||||||
ctx.arc(this.position.x, this.position.y, radius, 0, 2 * Math.PI);
|
|
||||||
ctx.fill();
|
|
||||||
}
|
}
|
||||||
} else {
|
let mag = 0.1
|
||||||
mech.fireCDcycle = mech.cycle + 10 //can't fire until after the explosion
|
if (game.cycle > this.endCycle - 5) {
|
||||||
|
mag = -0.22
|
||||||
// flashing lights to show armed
|
suck(mob, this.explodeRad * 3)
|
||||||
if (!(game.cycle % 10)) {
|
suck(body, this.explodeRad * 2)
|
||||||
if (this.isFlashOn) {
|
suck(powerUp, this.explodeRad * 1.5)
|
||||||
this.isFlashOn = false;
|
suck(bullet, this.explodeRad * 1.5)
|
||||||
} else {
|
suck([player], this.explodeRad * 1.3)
|
||||||
this.isFlashOn = true;
|
} else {
|
||||||
}
|
mag = 0.11
|
||||||
}
|
suck(mob, this.explodeRad * 3)
|
||||||
if (this.isFlashOn) {
|
suck(body, this.explodeRad * 2)
|
||||||
ctx.fillStyle = "#000";
|
suck(powerUp, this.explodeRad * 1.5)
|
||||||
ctx.beginPath();
|
suck(bullet, this.explodeRad * 1.5)
|
||||||
ctx.arc(this.position.x, this.position.y, this.radius, 0, 2 * Math.PI);
|
suck([player], this.explodeRad * 1.3)
|
||||||
ctx.fill();
|
|
||||||
//draw clock on timer
|
|
||||||
ctx.fillStyle = "#f04";
|
|
||||||
ctx.beginPath();
|
|
||||||
ctx.arc(this.position.x, this.position.y, this.radius * 0.7, 0, 2 * Math.PI);
|
|
||||||
ctx.fill();
|
|
||||||
}
|
}
|
||||||
|
//keep bomb in place
|
||||||
|
Matter.Body.setVelocity(this, {
|
||||||
|
x: 0,
|
||||||
|
y: 0
|
||||||
|
});
|
||||||
|
//draw suck
|
||||||
|
const radius = 2.75 * this.explodeRad * (this.endCycle - game.cycle) / suckCycles
|
||||||
|
ctx.fillStyle = "rgba(0,0,0,0.1)";
|
||||||
|
ctx.beginPath();
|
||||||
|
ctx.arc(this.position.x, this.position.y, radius, 0, 2 * Math.PI);
|
||||||
|
ctx.fill();
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@@ -2994,10 +2941,10 @@ const b = {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
Matter.Body.setVelocity(this, {
|
Matter.Body.setVelocity(this, {
|
||||||
x: -0.1 * this.velocity.x,
|
x: -0.5 * this.velocity.x,
|
||||||
y: -0.1 * this.velocity.y
|
y: -0.5 * this.velocity.y
|
||||||
});
|
});
|
||||||
Matter.Body.setDensity(this, 0.001);
|
// Matter.Body.setDensity(this, 0.001);
|
||||||
}
|
}
|
||||||
if (mod.isRailNails && this.speed > 10) {
|
if (mod.isRailNails && this.speed > 10) {
|
||||||
b.targetedNail(this.position, Math.min(40, this.speed) - 10)
|
b.targetedNail(this.position, Math.min(40, this.speed) - 10)
|
||||||
@@ -3212,8 +3159,13 @@ const b = {
|
|||||||
} else {
|
} else {
|
||||||
mech.fireCDcycle = mech.cycle
|
mech.fireCDcycle = mech.cycle
|
||||||
mech.energy -= mech.fieldRegen + mod.laserFieldDrain * mod.isLaserDiode
|
mech.energy -= mech.fieldRegen + mod.laserFieldDrain * mod.isLaserDiode
|
||||||
if (mod.isWideLaser) {
|
if (mod.wideLaser) {
|
||||||
const off = 8
|
ctx.strokeStyle = "#f00";
|
||||||
|
ctx.lineWidth = 8
|
||||||
|
ctx.globalAlpha = 0.5;
|
||||||
|
ctx.beginPath();
|
||||||
|
|
||||||
|
const off = 7.5
|
||||||
const dmg = 0.55 * mod.laserDamage // 3.5 * 0.55 = 200% more damage
|
const dmg = 0.55 * mod.laserDamage // 3.5 * 0.55 = 200% more damage
|
||||||
const where = {
|
const where = {
|
||||||
x: mech.pos.x + 20 * Math.cos(mech.angle),
|
x: mech.pos.x + 20 * Math.cos(mech.angle),
|
||||||
@@ -3223,7 +3175,7 @@ const b = {
|
|||||||
x: where.x + 3000 * Math.cos(mech.angle),
|
x: where.x + 3000 * Math.cos(mech.angle),
|
||||||
y: where.y + 3000 * Math.sin(mech.angle)
|
y: where.y + 3000 * Math.sin(mech.angle)
|
||||||
}, dmg, 0, true)
|
}, dmg, 0, true)
|
||||||
for (let i = 1; i < 3; i++) {
|
for (let i = 1; i < mod.wideLaser; i++) {
|
||||||
let whereOff = Vector.add(where, {
|
let whereOff = Vector.add(where, {
|
||||||
x: i * off * Math.cos(mech.angle + Math.PI / 2),
|
x: i * off * Math.cos(mech.angle + Math.PI / 2),
|
||||||
y: i * off * Math.sin(mech.angle + Math.PI / 2)
|
y: i * off * Math.sin(mech.angle + Math.PI / 2)
|
||||||
@@ -3241,6 +3193,8 @@ const b = {
|
|||||||
y: whereOff.y + 3000 * Math.sin(mech.angle)
|
y: whereOff.y + 3000 * Math.sin(mech.angle)
|
||||||
}, dmg, 0, true)
|
}, dmg, 0, true)
|
||||||
}
|
}
|
||||||
|
ctx.stroke();
|
||||||
|
ctx.globalAlpha = 1;
|
||||||
} else if (mod.beamSplitter) {
|
} else if (mod.beamSplitter) {
|
||||||
let dmg = mod.laserDamage * 0.9
|
let dmg = mod.laserDamage * 0.9
|
||||||
const where = {
|
const where = {
|
||||||
|
|||||||
20
js/level.js
20
js/level.js
@@ -7,6 +7,7 @@ const level = {
|
|||||||
defaultZoom: 1400,
|
defaultZoom: 1400,
|
||||||
onLevel: 0,
|
onLevel: 0,
|
||||||
levelsCleared: 0,
|
levelsCleared: 0,
|
||||||
|
bossKilled: false,
|
||||||
levels: ["skyscrapers", "rooftops", "warehouse", "highrise", "office", "aerie", "satellite", "sewers", "testChamber"],
|
levels: ["skyscrapers", "rooftops", "warehouse", "highrise", "office", "aerie", "satellite", "sewers", "testChamber"],
|
||||||
start() {
|
start() {
|
||||||
if (level.levelsCleared === 0) { //this code only runs on the first level
|
if (level.levelsCleared === 0) { //this code only runs on the first level
|
||||||
@@ -16,11 +17,11 @@ const level = {
|
|||||||
// game.setZoom();
|
// game.setZoom();
|
||||||
// mech.isCloak = true;
|
// mech.isCloak = true;
|
||||||
// mech.setField("wormhole")
|
// mech.setField("wormhole")
|
||||||
// b.giveGuns("flechettes")
|
// b.giveGuns("grenades")
|
||||||
// for (let i = 0; i < 10; i++) {
|
// for (let i = 0; i < 10; i++) {
|
||||||
// mod.giveMod("laser-bot");
|
// mod.giveMod("laser-bot");
|
||||||
// }
|
// }
|
||||||
// mod.giveMod("supercritical fission")
|
// mod.giveMod("vacuum bomb")
|
||||||
|
|
||||||
|
|
||||||
level.intro(); //starting level
|
level.intro(); //starting level
|
||||||
@@ -544,7 +545,7 @@ const level = {
|
|||||||
spawn.bodyRect(6800, 2490, 50, 50);
|
spawn.bodyRect(6800, 2490, 50, 50);
|
||||||
spawn.bodyRect(6800, 2540, 50, 50);
|
spawn.bodyRect(6800, 2540, 50, 50);
|
||||||
spawn.bodyRect(6800, 2590, 50, 50);
|
spawn.bodyRect(6800, 2590, 50, 50);
|
||||||
spawn.bodyRect(8225, 2225, 50, 375);
|
spawn.bodyRect(8225, 2225, 100, 100);
|
||||||
spawn.mapRect(6250, 1875, 700, 150);
|
spawn.mapRect(6250, 1875, 700, 150);
|
||||||
spawn.mapRect(8000, 1875, 600, 150);
|
spawn.mapRect(8000, 1875, 600, 150);
|
||||||
|
|
||||||
@@ -578,6 +579,7 @@ const level = {
|
|||||||
powerUps.addRerollToLevel() //needs to run after mobs are spawned
|
powerUps.addRerollToLevel() //needs to run after mobs are spawned
|
||||||
},
|
},
|
||||||
bosses() {
|
bosses() {
|
||||||
|
level.bossKilled = true; //if there is no boss this needs to be true to increase levels
|
||||||
level.custom = () => {
|
level.custom = () => {
|
||||||
level.playerExitCheck();
|
level.playerExitCheck();
|
||||||
};
|
};
|
||||||
@@ -639,6 +641,7 @@ const level = {
|
|||||||
powerUps.addRerollToLevel() //needs to run after mobs are spawned
|
powerUps.addRerollToLevel() //needs to run after mobs are spawned
|
||||||
},
|
},
|
||||||
intro() {
|
intro() {
|
||||||
|
level.bossKilled = true; //if there is no boss this needs to be true to increase levels
|
||||||
level.custom = () => {
|
level.custom = () => {
|
||||||
level.playerExitCheck();
|
level.playerExitCheck();
|
||||||
};
|
};
|
||||||
@@ -1477,7 +1480,7 @@ const level = {
|
|||||||
spawn.randomMob(3600, -500, 0.8);
|
spawn.randomMob(3600, -500, 0.8);
|
||||||
spawn.randomMob(3400, -200, 0.8);
|
spawn.randomMob(3400, -200, 0.8);
|
||||||
spawn.randomMob(1650, -1300, 0.7)
|
spawn.randomMob(1650, -1300, 0.7)
|
||||||
spawn.randomMob(-4100, -50, 0.7);
|
spawn.randomMob(4100, -50, 0.7);
|
||||||
spawn.randomMob(4100, -50, 0.5);
|
spawn.randomMob(4100, -50, 0.5);
|
||||||
spawn.randomMob(1700, -50, 0.3)
|
spawn.randomMob(1700, -50, 0.3)
|
||||||
spawn.randomMob(2350, -900, 0.3)
|
spawn.randomMob(2350, -900, 0.3)
|
||||||
@@ -3882,15 +3885,18 @@ const level = {
|
|||||||
},
|
},
|
||||||
custom() {}, //each level runs it's own custom code (level exits, ...)
|
custom() {}, //each level runs it's own custom code (level exits, ...)
|
||||||
nextLevel() {
|
nextLevel() {
|
||||||
level.levelsCleared++;
|
if (level.bossKilled || level.levelsCleared < level.levels.length) {
|
||||||
level.onLevel++; //cycles map to next level
|
level.levelsCleared++;
|
||||||
if (level.onLevel > level.levels.length - 1) level.onLevel = 0;
|
level.onLevel++; //cycles map to next level
|
||||||
|
if (level.onLevel > level.levels.length - 1) level.onLevel = 0;
|
||||||
|
}
|
||||||
level.difficultyIncrease(game.difficultyMode) //increase difficulty based on modes
|
level.difficultyIncrease(game.difficultyMode) //increase difficulty based on modes
|
||||||
if (level.levelsCleared > level.levels.length) level.difficultyIncrease(game.difficultyMode)
|
if (level.levelsCleared > level.levels.length) level.difficultyIncrease(game.difficultyMode)
|
||||||
if (level.levelsCleared > level.levels.length * 1.25) level.difficultyIncrease(game.difficultyMode)
|
if (level.levelsCleared > level.levels.length * 1.25) level.difficultyIncrease(game.difficultyMode)
|
||||||
if (level.levelsCleared > level.levels.length * 1.5) level.difficultyIncrease(game.difficultyMode)
|
if (level.levelsCleared > level.levels.length * 1.5) level.difficultyIncrease(game.difficultyMode)
|
||||||
if (level.levelsCleared > level.levels.length * 2) level.difficultyIncrease(game.difficultyMode)
|
if (level.levelsCleared > level.levels.length * 2) level.difficultyIncrease(game.difficultyMode)
|
||||||
if (game.isEasyMode && level.levelsCleared % 2) level.difficultyDecrease(1);
|
if (game.isEasyMode && level.levelsCleared % 2) level.difficultyDecrease(1);
|
||||||
|
level.bossKilled = false;
|
||||||
//reset lost mod display
|
//reset lost mod display
|
||||||
for (let i = 0; i < mod.mods.length; i++) {
|
for (let i = 0; i < mod.mods.length; i++) {
|
||||||
if (mod.mods[i].isLost) mod.mods[i].isLost = false;
|
if (mod.mods[i].isLost) mod.mods[i].isLost = false;
|
||||||
|
|||||||
@@ -1104,7 +1104,7 @@ const mobs = {
|
|||||||
//replace dead mob with a regular body
|
//replace dead mob with a regular body
|
||||||
replace(i) {
|
replace(i) {
|
||||||
//if there are too many bodies don't turn into blocks to help performance
|
//if there are too many bodies don't turn into blocks to help performance
|
||||||
if (this.leaveBody && body.length < 60 && this.mass < 200) {
|
if (this.leaveBody && body.length < 60 && this.mass < 200 && this.radius > 18) {
|
||||||
const len = body.length;
|
const len = body.length;
|
||||||
const v = Matter.Vertices.hull(Matter.Vertices.clockwiseSort(this.vertices)) //might help with vertex collision issue, not sure
|
const v = Matter.Vertices.hull(Matter.Vertices.clockwiseSort(this.vertices)) //might help with vertex collision issue, not sure
|
||||||
body[len] = Matter.Bodies.fromVertices(this.position.x, this.position.y, v);
|
body[len] = Matter.Bodies.fromVertices(this.position.x, this.position.y, v);
|
||||||
|
|||||||
83
js/mods.js
83
js/mods.js
@@ -320,9 +320,9 @@ const mod = {
|
|||||||
maxCount: 1,
|
maxCount: 1,
|
||||||
count: 0,
|
count: 0,
|
||||||
allowed() {
|
allowed() {
|
||||||
return true
|
return mech.fieldUpgrades[mech.fieldMode].name !== "wormhole"
|
||||||
},
|
},
|
||||||
requires: "",
|
requires: "not wormhole",
|
||||||
effect() {
|
effect() {
|
||||||
mod.throwChargeRate = 2
|
mod.throwChargeRate = 2
|
||||||
},
|
},
|
||||||
@@ -832,7 +832,7 @@ const mod = {
|
|||||||
maxCount: 1,
|
maxCount: 1,
|
||||||
count: 0,
|
count: 0,
|
||||||
allowed() {
|
allowed() {
|
||||||
return mod.totalBots() > 1 || mod.haveGunCheck("drone") || mod.haveGunCheck("mine") || mod.haveGunCheck("spores") || mech.fieldUpgrades[mech.fieldMode].name === "nano-scale manufacturing"
|
return (mod.totalBots() > 1 || mod.haveGunCheck("drone") || mod.haveGunCheck("mine") || mod.haveGunCheck("spores") || mech.fieldUpgrades[mech.fieldMode].name === "nano-scale manufacturing") && !mod.isEnergyHealth
|
||||||
},
|
},
|
||||||
requires: "drones, spores, mines, or bots",
|
requires: "drones, spores, mines, or bots",
|
||||||
effect() {
|
effect() {
|
||||||
@@ -850,7 +850,7 @@ const mod = {
|
|||||||
allowed() {
|
allowed() {
|
||||||
return mod.isNoFireDefense
|
return mod.isNoFireDefense
|
||||||
},
|
},
|
||||||
requires: "full annealing",
|
requires: "decorrelation",
|
||||||
effect() {
|
effect() {
|
||||||
mod.isNoFireDamage = true
|
mod.isNoFireDamage = true
|
||||||
},
|
},
|
||||||
@@ -2015,9 +2015,9 @@ const mod = {
|
|||||||
maxCount: 1,
|
maxCount: 1,
|
||||||
count: 0,
|
count: 0,
|
||||||
allowed() {
|
allowed() {
|
||||||
return mod.haveGunCheck("grenades")
|
return mod.haveGunCheck("grenades") && !mod.isVacuumBomb
|
||||||
},
|
},
|
||||||
requires: "grenades",
|
requires: "grenades, not vacuum bomb",
|
||||||
effect() {
|
effect() {
|
||||||
mod.isRPG = true;
|
mod.isRPG = true;
|
||||||
},
|
},
|
||||||
@@ -2026,21 +2026,43 @@ const mod = {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "electromagnetic pulse",
|
name: "vacuum bomb",
|
||||||
description: "<strong>vacuum bomb's </strong> <strong class='color-e'>explosion</strong> removes<br><strong>80%</strong> of <strong>shields</strong> and <strong>100%</strong> of <strong class='color-f'>energy</strong>",
|
description: "<strong>grenades</strong> fire slower, <strong class='color-e'>explode</strong> bigger<br> and, <strong>suck</strong> everything towards them",
|
||||||
maxCount: 1,
|
maxCount: 1,
|
||||||
count: 0,
|
count: 0,
|
||||||
allowed() {
|
allowed() {
|
||||||
return mod.haveGunCheck("vacuum bomb")
|
return mod.haveGunCheck("grenades") && !mod.isRPG
|
||||||
},
|
},
|
||||||
requires: "vacuum bomb",
|
requires: "grenades, not rocket-propelled",
|
||||||
effect() {
|
effect() {
|
||||||
mod.isVacuumShield = true;
|
mod.isVacuumBomb = true;
|
||||||
|
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
|
||||||
|
if (b.guns[i].name === "grenades") b.guns[i].fire = b.guns[i].fireVacuum
|
||||||
|
}
|
||||||
},
|
},
|
||||||
remove() {
|
remove() {
|
||||||
mod.isVacuumShield = false;
|
mod.isVacuumBomb = false;
|
||||||
|
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
|
||||||
|
if (b.guns[i].name === "grenades") b.guns[i].fire = b.guns[i].fireNormal
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
// {
|
||||||
|
// name: "electromagnetic pulse",
|
||||||
|
// description: "<strong>vacuum bomb's </strong> <strong class='color-e'>explosion</strong> removes<br><strong>80%</strong> of <strong>shields</strong> and <strong>100%</strong> of <strong class='color-f'>energy</strong>",
|
||||||
|
// maxCount: 1,
|
||||||
|
// count: 0,
|
||||||
|
// allowed() {
|
||||||
|
// return mod.haveGunCheck("vacuum bomb")
|
||||||
|
// },
|
||||||
|
// requires: "vacuum bomb",
|
||||||
|
// effect() {
|
||||||
|
// mod.isVacuumShield = true;
|
||||||
|
// },
|
||||||
|
// remove() {
|
||||||
|
// mod.isVacuumShield = false;
|
||||||
|
// }
|
||||||
|
// },
|
||||||
{
|
{
|
||||||
name: "water shielding",
|
name: "water shielding",
|
||||||
description: "increase <strong>neutron bomb's</strong> range by <strong>20%</strong><br>player is <strong>immune</strong> to its harmful effects",
|
description: "increase <strong>neutron bomb's</strong> range by <strong>20%</strong><br>player is <strong>immune</strong> to its harmful effects",
|
||||||
@@ -2268,7 +2290,7 @@ const mod = {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "thermoelectric effect",
|
name: "thermoelectric effect",
|
||||||
description: "<strong>killing</strong> mobs with <strong>ice IX</strong> gives <strong>4%</strong> <strong class='color-h'>health</strong><br>and overloads <strong class='color-f'>energy</strong> by <strong>100%</strong> of your max",
|
description: "<strong>killing</strong> mobs with <strong>ice IX</strong> gives <strong>4%</strong> <strong class='color-h'>health</strong><br>and overloads <strong class='color-f'>energy</strong> by <strong>166%</strong> of your max",
|
||||||
maxCount: 9,
|
maxCount: 9,
|
||||||
count: 0,
|
count: 0,
|
||||||
allowed() {
|
allowed() {
|
||||||
@@ -2442,13 +2464,34 @@ const mod = {
|
|||||||
},
|
},
|
||||||
requires: "laser, not specular reflection",
|
requires: "laser, not specular reflection",
|
||||||
effect() {
|
effect() {
|
||||||
mod.isWideLaser = true
|
if (mod.wideLaser === 0) mod.wideLaser = 3
|
||||||
|
mod.isWideLaser = true;
|
||||||
},
|
},
|
||||||
remove() {
|
remove() {
|
||||||
mod.isWideLaser = false
|
mod.wideLaser = 0
|
||||||
|
mod.isWideLaser = false;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "output coupler",
|
||||||
|
description: "diffuse <strong>laser</strong> beam is <strong>30%</strong> <strong>wider</strong><br> and the full beam does <strong>30%</strong> more <strong class='color-d'>damage</strong>",
|
||||||
|
maxCount: 1,
|
||||||
|
count: 0,
|
||||||
|
allowed() {
|
||||||
|
return mod.haveGunCheck("laser") && mod.isWideLaser
|
||||||
|
},
|
||||||
|
requires: "laser, not specular reflection",
|
||||||
|
effect() {
|
||||||
|
mod.wideLaser = 4
|
||||||
|
},
|
||||||
|
remove() {
|
||||||
|
if (mod.isWideLaser) {
|
||||||
|
mod.wideLaser = 3
|
||||||
|
} else {
|
||||||
|
mod.wideLaser = 0
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
// {
|
// {
|
||||||
// name: "waste heat recovery",
|
// name: "waste heat recovery",
|
||||||
// description: "<strong>laser</strong> <strong class='color-d'>damage</strong> grows by <strong>400%</strong> as you fire<br>but you periodically <strong>eject</strong> your <strong class='color-h'>health</strong>",
|
// description: "<strong>laser</strong> <strong class='color-d'>damage</strong> grows by <strong>400%</strong> as you fire<br>but you periodically <strong>eject</strong> your <strong class='color-h'>health</strong>",
|
||||||
@@ -2855,7 +2898,7 @@ const mod = {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Penrose process",
|
name: "Penrose process",
|
||||||
description: "after a <strong>block</strong> falls into a <strong class='color-worm'>wormhole</strong><br>your <strong class='color-f'>energy</strong> overfills to <strong>300%</strong> of the maximum",
|
description: "after a <strong>block</strong> falls into a <strong class='color-worm'>wormhole</strong><br>your <strong class='color-f'>energy</strong> overfills to <strong>200%</strong> of the maximum",
|
||||||
maxCount: 1,
|
maxCount: 1,
|
||||||
count: 0,
|
count: 0,
|
||||||
allowed() {
|
allowed() {
|
||||||
@@ -3057,7 +3100,7 @@ const mod = {
|
|||||||
isHarmDamage: null,
|
isHarmDamage: null,
|
||||||
isHeavyWater: null,
|
isHeavyWater: null,
|
||||||
energyRegen: null,
|
energyRegen: null,
|
||||||
isVacuumShield: null,
|
isVacuumBomb: null,
|
||||||
renormalization: null,
|
renormalization: null,
|
||||||
grenadeFragments: null,
|
grenadeFragments: null,
|
||||||
isEnergyDamage: null,
|
isEnergyDamage: null,
|
||||||
@@ -3143,5 +3186,7 @@ const mod = {
|
|||||||
isNailCrit: null,
|
isNailCrit: null,
|
||||||
isFlechetteExplode: null,
|
isFlechetteExplode: null,
|
||||||
isWormSpores: null,
|
isWormSpores: null,
|
||||||
isWormBullets: null
|
isWormBullets: null,
|
||||||
|
isWideLaser: null,
|
||||||
|
wideLaser: null
|
||||||
}
|
}
|
||||||
36
js/player.js
36
js/player.js
@@ -785,8 +785,15 @@ const mech = {
|
|||||||
ctx.fillRect(xOff, yOff, range * mech.maxEnergy, 10);
|
ctx.fillRect(xOff, yOff, range * mech.maxEnergy, 10);
|
||||||
ctx.fillStyle = mech.fieldMeterColor;
|
ctx.fillStyle = mech.fieldMeterColor;
|
||||||
ctx.fillRect(xOff, yOff, range * mech.energy, 10);
|
ctx.fillRect(xOff, yOff, range * mech.energy, 10);
|
||||||
|
if (mech.energy < 0) mech.energy = 0
|
||||||
|
} else if (mech.energy > mech.maxEnergy + 0.05) {
|
||||||
|
ctx.fillStyle = bgColor;
|
||||||
|
const xOff = mech.pos.x - mech.radius * mech.energy
|
||||||
|
const yOff = mech.pos.y - 50
|
||||||
|
// ctx.fillRect(xOff, yOff, range * mech.maxEnergy, 10);
|
||||||
|
ctx.fillStyle = mech.fieldMeterColor;
|
||||||
|
ctx.fillRect(xOff, yOff, range * mech.energy, 10);
|
||||||
}
|
}
|
||||||
if (mech.energy < 0) mech.energy = 0
|
|
||||||
// else {
|
// else {
|
||||||
// mech.energy = mech.maxEnergy
|
// mech.energy = mech.maxEnergy
|
||||||
// }
|
// }
|
||||||
@@ -2328,7 +2335,7 @@ const mech = {
|
|||||||
Matter.World.remove(engine.world, body[i]);
|
Matter.World.remove(engine.world, body[i]);
|
||||||
body.splice(i, 1);
|
body.splice(i, 1);
|
||||||
mech.fieldRange *= 0.8
|
mech.fieldRange *= 0.8
|
||||||
if (mod.isWormholeEnergy && mech.energy < mech.maxEnergy * 3) mech.energy = mech.maxEnergy * 3
|
if (mod.isWormholeEnergy && mech.energy < mech.maxEnergy * 2) mech.energy = mech.maxEnergy * 2
|
||||||
if (mod.isWormSpores) { //pandimensionalspermia
|
if (mod.isWormSpores) { //pandimensionalspermia
|
||||||
b.spore(Vector.add(mech.hole.pos2, Vector.rotate({
|
b.spore(Vector.add(mech.hole.pos2, Vector.rotate({
|
||||||
x: mech.fieldRange,
|
x: mech.fieldRange,
|
||||||
@@ -2351,7 +2358,7 @@ const mech = {
|
|||||||
Matter.World.remove(engine.world, body[i]);
|
Matter.World.remove(engine.world, body[i]);
|
||||||
body.splice(i, 1);
|
body.splice(i, 1);
|
||||||
mech.fieldRange *= 0.8
|
mech.fieldRange *= 0.8
|
||||||
if (mod.isWormholeEnergy && mech.energy < mech.maxEnergy * 3) mech.energy = mech.maxEnergy * 3
|
if (mod.isWormholeEnergy && mech.energy < mech.maxEnergy * 2) mech.energy = mech.maxEnergy * 2
|
||||||
if (mod.isWormSpores) { //pandimensionalspermia
|
if (mod.isWormSpores) { //pandimensionalspermia
|
||||||
b.spore(Vector.add(mech.hole.pos1, Vector.rotate({
|
b.spore(Vector.add(mech.hole.pos1, Vector.rotate({
|
||||||
x: mech.fieldRange,
|
x: mech.fieldRange,
|
||||||
@@ -2396,13 +2403,30 @@ const mech = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (input.field && mech.fieldCDcycle < mech.cycle) { //not hold but field button is pressed
|
if (input.field && mech.fieldCDcycle < mech.cycle) { //not hold but field button is pressed
|
||||||
|
const justPastMouse = Vector.add(Vector.mult(Vector.normalise(Vector.sub(game.mouseInGame, mech.pos)), 50), game.mouseInGame)
|
||||||
|
const scale = 60
|
||||||
|
// console.log(Matter.Query.region(map, bounds))
|
||||||
if (mech.hole.isReady &&
|
if (mech.hole.isReady &&
|
||||||
(Matter.Query.ray(map, mech.pos, game.mouseInGame).length === 0 &&
|
(
|
||||||
Matter.Query.ray(map, mech.pos, Vector.add(Vector.mult(Vector.normalise(Vector.sub(game.mouseInGame, mech.pos)), 50), game.mouseInGame)).length === 0)
|
Matter.Query.region(map, {
|
||||||
|
min: {
|
||||||
|
x: game.mouseInGame.x - scale,
|
||||||
|
y: game.mouseInGame.y - scale
|
||||||
|
},
|
||||||
|
max: {
|
||||||
|
x: game.mouseInGame.x + scale,
|
||||||
|
y: game.mouseInGame.y + scale
|
||||||
|
}
|
||||||
|
}).length === 0 &&
|
||||||
|
Matter.Query.ray(map, mech.pos, justPastMouse).length === 0
|
||||||
|
// Matter.Query.ray(map, mech.pos, game.mouseInGame).length === 0 &&
|
||||||
|
// Matter.Query.ray(map, player.position, game.mouseInGame).length === 0 &&
|
||||||
|
// Matter.Query.ray(map, player.position, justPastMouse).length === 0
|
||||||
|
)
|
||||||
) {
|
) {
|
||||||
const sub = Vector.sub(game.mouseInGame, mech.pos)
|
const sub = Vector.sub(game.mouseInGame, mech.pos)
|
||||||
const mag = Vector.magnitude(sub)
|
const mag = Vector.magnitude(sub)
|
||||||
const drain = 0.06 + 0.007 * Math.sqrt(mag)
|
const drain = 0.07 + 0.008 * Math.sqrt(mag)
|
||||||
if (mech.energy > drain && mag > 300) {
|
if (mech.energy > drain && mag > 300) {
|
||||||
mech.energy -= drain
|
mech.energy -= drain
|
||||||
mech.hole.isReady = false;
|
mech.hole.isReady = false;
|
||||||
|
|||||||
@@ -461,6 +461,7 @@ const powerUps = {
|
|||||||
},
|
},
|
||||||
randomPowerUpCounter: 0,
|
randomPowerUpCounter: 0,
|
||||||
spawnBossPowerUp(x, y) { //boss spawns field and gun mod upgrades
|
spawnBossPowerUp(x, y) { //boss spawns field and gun mod upgrades
|
||||||
|
level.bossKilled = true;
|
||||||
// if (game.difficultyMode === 4) powerUps.spawn(x, y, "mod") //why mode gets a free mod
|
// if (game.difficultyMode === 4) powerUps.spawn(x, y, "mod") //why mode gets a free mod
|
||||||
powerUps.randomPowerUpCounter++;
|
powerUps.randomPowerUpCounter++;
|
||||||
const chanceToFail = Math.max(level.levelsCleared, 10) * 0.1 //1 until level 10, then 1.1, 1.2, 1.3, ...
|
const chanceToFail = Math.max(level.levelsCleared, 10) * 0.1 //1 until level 10, then 1.1, 1.2, 1.3, ...
|
||||||
@@ -471,8 +472,8 @@ const powerUps = {
|
|||||||
spawnHealthAmmo()
|
spawnHealthAmmo()
|
||||||
}
|
}
|
||||||
if (game.difficultyMode === 4) {
|
if (game.difficultyMode === 4) {
|
||||||
powerUps.randomPowerUpCounter++;
|
powerUps.randomPowerUpCounter + 0.6;
|
||||||
const chanceToFail = Math.max(level.levelsCleared, 10) * 0.1 //1 until level 10, then 1.1, 1.2, 1.3, ...
|
const chanceToFail = Math.max(level.levelsCleared, 6) * 0.1 //1 until level 8
|
||||||
if (Math.random() * chanceToFail < powerUps.randomPowerUpCounter) {
|
if (Math.random() * chanceToFail < powerUps.randomPowerUpCounter) {
|
||||||
powerUps.randomPowerUpCounter = 0;
|
powerUps.randomPowerUpCounter = 0;
|
||||||
spawnPowerUps()
|
spawnPowerUps()
|
||||||
|
|||||||
44
todo.txt
44
todo.txt
@@ -1,13 +1,29 @@
|
|||||||
|
|
||||||
|
gun: vacuum bomb is removed
|
||||||
|
mod: vacuum bomb - grenades fire slower, explode bigger and, suck everything towards them
|
||||||
|
|
||||||
|
laser and diffuse laser graphics are better
|
||||||
|
mod: output coupler - diffuse laser beam is 30% wider and does 30% more damage
|
||||||
|
requires diffuse beam
|
||||||
|
|
||||||
|
level number doesn't increase if you skip the boss (in the late game)
|
||||||
|
|
||||||
************** TODO - n-gon **************
|
************** TODO - n-gon **************
|
||||||
|
|
||||||
foam bullet on dmg shrink effect
|
add an ending to the game
|
||||||
|
revamp the boss level, or add a new final level
|
||||||
|
final level requires you to kill something
|
||||||
|
so skipping content is only smart if you are strong enough to beat the final boss
|
||||||
|
around level 15
|
||||||
|
game never ends if you have used cheats
|
||||||
|
|
||||||
|
new status effect - apply status effect to mobs that makes blocks attracted to them
|
||||||
|
only lasts a few cycles
|
||||||
|
|
||||||
|
foam or spore bullet on dmg shrink effect
|
||||||
it might mess with the foam position of other bullets on the mob
|
it might mess with the foam position of other bullets on the mob
|
||||||
shrink when foam bullets end while attached, or shrink on collision?
|
shrink when foam bullets end while attached, or shrink on collision?
|
||||||
|
|
||||||
effect - shrink or grow things
|
|
||||||
|
|
||||||
time dilation mod rework / buff (time dilation is cool, but it can feel like a chore)
|
time dilation mod rework / buff (time dilation is cool, but it can feel like a chore)
|
||||||
redistribute effects
|
redistribute effects
|
||||||
take no damage
|
take no damage
|
||||||
@@ -16,13 +32,7 @@ time dilation mod rework / buff (time dilation is cool, but it can feel like a c
|
|||||||
33% move jump fire always
|
33% move jump fire always
|
||||||
|
|
||||||
mod - after a mob or shield dies, remaining dots look for a new nearby host
|
mod - after a mob or shield dies, remaining dots look for a new nearby host
|
||||||
|
or mod: radiation effects can spread to nearby mobs
|
||||||
add an ending to the game
|
|
||||||
revamp the boss level, or add a new final level
|
|
||||||
final level requires you to kill something
|
|
||||||
so skipping content is only smart if you are strong enough to beat the final boss
|
|
||||||
around level 15
|
|
||||||
game never ends if you have used cheats
|
|
||||||
|
|
||||||
look for mods that could update description text with count and mod.is information
|
look for mods that could update description text with count and mod.is information
|
||||||
can only use variables that change in effect() and remove()
|
can only use variables that change in effect() and remove()
|
||||||
@@ -32,8 +42,6 @@ mod self destruct - drones explode when they die, but they last 1/2 as long
|
|||||||
|
|
||||||
mouse event e.which is deprecated
|
mouse event e.which is deprecated
|
||||||
|
|
||||||
vacuum bomb applies status effect to mobs that makes blocks attracted to them
|
|
||||||
|
|
||||||
mod: take less harm if you are moving fast
|
mod: take less harm if you are moving fast
|
||||||
require squirrel cage rotor
|
require squirrel cage rotor
|
||||||
|
|
||||||
@@ -74,8 +82,6 @@ a bot that eats up health and ammo, but poops a reroll after picking up 2 power
|
|||||||
disable crystalized armor?
|
disable crystalized armor?
|
||||||
could convert rerolls, ammo, and health into mods instead
|
could convert rerolls, ammo, and health into mods instead
|
||||||
|
|
||||||
mod: radiation effects can spread to nearby mobs
|
|
||||||
|
|
||||||
mod: foam is attracted to mobs
|
mod: foam is attracted to mobs
|
||||||
use a gravitational attraction model?
|
use a gravitational attraction model?
|
||||||
could foam be attracted to other foam bullets too?
|
could foam be attracted to other foam bullets too?
|
||||||
@@ -229,18 +235,8 @@ an effect when canceling a power up
|
|||||||
add player Scent Trails for mob navigation
|
add player Scent Trails for mob navigation
|
||||||
https://abitawake.com/news/articles/enemy-ai-chasing-a-player-without-navigation2d-or-a-star-pathfinding
|
https://abitawake.com/news/articles/enemy-ai-chasing-a-player-without-navigation2d-or-a-star-pathfinding
|
||||||
|
|
||||||
settings - custom keys binding
|
|
||||||
|
|
||||||
css transition for pause menu
|
css transition for pause menu
|
||||||
|
|
||||||
gun: Spirit Bomb (singularity)
|
|
||||||
use charge up like rail gun
|
|
||||||
electricity graphics like plasma torch
|
|
||||||
suck in nearby mobs, power ups?, blocks?
|
|
||||||
sucked in stuff increase size
|
|
||||||
uses energy
|
|
||||||
hold above the player's head
|
|
||||||
|
|
||||||
animate new level spawn by having the map aspects randomly fly into place
|
animate new level spawn by having the map aspects randomly fly into place
|
||||||
|
|
||||||
n-gon outreach ideas
|
n-gon outreach ideas
|
||||||
|
|||||||
Reference in New Issue
Block a user