minimal HUD

setting - minimal HUD
  remove: defense bar, damage bar, tech, in game console

improved text clarity on coupling
removed tech decoupling

added cloaking and sneak attack graphics
  also, the 50% defense when cloaked is now clear from the defense bar
ternary 44->83% damage but requires current gun to have ammo/3 (was any gun)
wormhole invariant: uses much less energy to pause time
standing wave has less recoil when blocking

new images
bug fixes
This commit is contained in:
landgreen
2023-04-26 19:36:33 -07:00
parent 1b23dec950
commit 0b728fb02c
25 changed files with 759 additions and 606 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.9 KiB

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 38 KiB

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 35 KiB

After

Width:  |  Height:  |  Size: 67 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 32 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 22 KiB

After

Width:  |  Height:  |  Size: 55 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 41 KiB

After

Width:  |  Height:  |  Size: 39 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 25 KiB

After

Width:  |  Height:  |  Size: 35 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 27 KiB

After

Width:  |  Height:  |  Size: 56 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 41 KiB

After

Width:  |  Height:  |  Size: 66 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 37 KiB

After

Width:  |  Height:  |  Size: 48 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 25 KiB

After

Width:  |  Height:  |  Size: 57 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 53 KiB

View File

@@ -70,12 +70,15 @@
<label for="seed" title="the randoms seed determines level order, tech choices, and mob types">randomization seed:</label> <label for="seed" title="the randoms seed determines level order, tech choices, and mob types">randomization seed:</label>
<input type="text" id="seed" name="seed" autocomplete="off" spellcheck="false" minlength="1" style="width: 120px;"> <input type="text" id="seed" name="seed" autocomplete="off" spellcheck="false" minlength="1" style="width: 120px;">
<br> <br>
<label for="hide-images" title="hide images for fields, guns, and tech">hide images:</label>
<input onclick="build.showImages('settings')" type="checkbox" id="hide-images" name="hide-images" style="width:17px; height:17px;">
<br>
<span id="previous-seed" style="color:#bbb"></span> <span id="previous-seed" style="color:#bbb"></span>
<label for="community-maps" title="add about 12 player made levels the random n-gon level pool">include community maps:</label> <input onclick="build.showImages('settings')" type="checkbox" id="hide-images" name="hide-images" style="width:17px; height:17px;">
<label for="hide-images" title="hide images for fields, guns, and tech">hide images</label>
<br>
<input onclick="build.hideHUD('settings')" type="checkbox" id="hide-hud" name="hide-hud" style="width:17px; height:17px;">
<label for="hide-hud" title="hide: tech, defense, damage, in game console">minimal HUD</label>
<br>
<input type="checkbox" id="community-maps" name="community-maps" style="width:17px; height:17px;"> <input type="checkbox" id="community-maps" name="community-maps" style="width:17px; height:17px;">
<label for="community-maps" title="add about 12 player made levels the random n-gon level pool">community maps</label>
<!-- <br> <!-- <br>
<label for="body-damage" title="allow damage from the ground and large fast moving blocks">collision damage from blocks:</label> <label for="body-damage" title="allow damage from the ground and large fast moving blocks">collision damage from blocks:</label>

View File

@@ -333,8 +333,8 @@ const b = {
// ctx.fill(); // ctx.fill();
simulation.drawList.push({ //add dmg to draw queue simulation.drawList.push({ //add dmg to draw queue
x: m.pos.x + 35 * Math.cos(m.angle), x: m.pos.x + 20 * Math.cos(m.angle),
y: m.pos.y + 35 * Math.sin(m.angle), y: m.pos.y + 20 * Math.sin(m.angle),
radius: radius, radius: radius,
color: "#fb0", color: "#fb0",
time: 1 time: 1
@@ -1747,9 +1747,14 @@ const b = {
x: player.velocity.x * 0.8, x: player.velocity.x * 0.8,
y: player.velocity.y * 0.8 y: player.velocity.y * 0.8
}); });
const pull = Vector.mult(Vector.normalise(sub), 0.0008 * Math.min(Math.max(15, dist), 200))
player.force.x += pull.x
player.force.y += pull.y //need to scale the friction differently based on distance?
if (dist > 500) {
const pull = Vector.mult(Vector.normalise(sub), 0.0008 * Math.min(Math.max(15, dist), 200))
player.force.x += pull.x
player.force.y += pull.y
}
if (dist > 500) { if (dist > 500) {
m.energy -= this.drain m.energy -= this.drain
@@ -1806,6 +1811,321 @@ const b = {
}); });
Composite.add(engine.world, bullet[me]); //add bullet to world Composite.add(engine.world, bullet[me]); //add bullet to world
}, },
// grapple(where, angle = m.angle, harpoonSize = 1) {
// const me = bullet.length;
// const returnRadius = 100 * Math.sqrt(harpoonSize)
// bullet[me] = Bodies.fromVertices(where.x, where.y, [{
// x: -50 * harpoonSize,
// y: 2 * harpoonSize,
// index: 0,
// isInternal: false
// }, {
// x: -50 * harpoonSize,
// y: -2 * harpoonSize,
// index: 1,
// isInternal: false
// }, {
// x: 45 * harpoonSize,
// y: -3 * harpoonSize,
// index: 2,
// isInternal: false
// }, {
// x: 50 * harpoonSize,
// y: 0,
// index: 3,
// isInternal: false
// }, {
// x: 45 * harpoonSize,
// y: 3 * harpoonSize,
// index: 4,
// isInternal: false
// }], {
// angle: angle,
// friction: 1,
// frictionAir: 0.4,
// thrustMag: 0.1,
// dmg: 6, //damage done in addition to the damage from momentum
// classType: "bullet",
// endCycle: simulation.cycle + 70,
// collisionFilter: {
// category: cat.bullet,
// mask: tech.isShieldPierce ? cat.body | cat.mob | cat.mobBullet : cat.body | cat.mob | cat.mobBullet | cat.mobShield,
// },
// minDmgSpeed: 4,
// lookFrequency: Math.floor(7 + Math.random() * 3),
// density: tech.harpoonDensity, //0.001 is normal for blocks, 0.004 is normal for harpoon, 0.004*6 when buffed
// drain: tech.isRailEnergy ? 0.0006 : 0.006,
// beforeDmg(who) {
// if (tech.isShieldPierce && who.isShielded) { //disable shields
// who.isShielded = false
// requestAnimationFrame(() => {
// who.isShielded = true
// });
// }
// if (tech.fragments) {
// b.targetedNail(this.vertices[2], tech.fragments * Math.floor(2 + Math.random()))
// }
// if (tech.isFoamBall) {
// for (let i = 0, len = 4 * this.mass; i < len; i++) {
// const radius = 5 + 8 * Math.random()
// const velocity = {
// x: Math.max(0.5, 2 - radius * 0.1),
// y: 0
// }
// b.foam(this.position, Vector.rotate(velocity, 6.28 * Math.random()), radius)
// }
// // this.endCycle = 0;
// }
// },
// caughtPowerUp: null,
// dropCaughtPowerUp() {
// if (this.caughtPowerUp) {
// this.caughtPowerUp.collisionFilter.category = cat.powerUp
// this.caughtPowerUp.collisionFilter.mask = cat.map | cat.powerUp
// this.caughtPowerUp = null
// }
// },
// onEnd() {
// if (this.caughtPowerUp && !simulation.isChoosing && (this.caughtPowerUp.name !== "heal" || m.health !== m.maxHealth || tech.isOverHeal)) {
// let index = null //find index
// for (let i = 0, len = powerUp.length; i < len; ++i) {
// if (powerUp[i] === this.caughtPowerUp) index = i
// }
// if (index !== null) {
// powerUps.onPickUp(this.caughtPowerUp);
// this.caughtPowerUp.effect();
// Matter.Composite.remove(engine.world, this.caughtPowerUp);
// powerUp.splice(index, 1);
// if (tech.isHarpoonPowerUp) tech.harpoonDensity = 0.004 * 6 //0.005 is normal
// } else {
// this.dropCaughtPowerUp()
// }
// } else {
// this.dropCaughtPowerUp()
// }
// },
// draw() {
// const where = {
// x: m.pos.x + 30 * Math.cos(m.angle),
// y: m.pos.y + 30 * Math.sin(m.angle)
// }
// const sub = Vector.sub(where, this.vertices[0])
// const controlPoint = Vector.add(where, Vector.mult(sub, -0.5))
// ctx.strokeStyle = "#000" // "#0ce"
// ctx.lineWidth = 0.5
// ctx.beginPath();
// ctx.moveTo(where.x, where.y);
// ctx.quadraticCurveTo(controlPoint.x, controlPoint.y, this.vertices[0].x, this.vertices[0].y)
// // ctx.lineTo(this.vertices[0].x, this.vertices[0].y);
// ctx.stroke();
// //draw harpoon spikes
// const spikeLength = 2
// ctx.beginPath();
// const spike1 = Vector.add(this.vertices[1], Vector.mult(Vector.sub(this.vertices[1], this.vertices[2]), spikeLength))
// ctx.moveTo(this.vertices[2].x, this.vertices[2].y);
// ctx.lineTo(spike1.x, spike1.y);
// ctx.lineTo(this.vertices[3].x, this.vertices[3].y);
// const spike2 = Vector.add(this.vertices[3], Vector.mult(Vector.sub(this.vertices[3], this.vertices[2]), spikeLength))
// ctx.moveTo(this.vertices[2].x, this.vertices[2].y);
// ctx.lineTo(spike2.x, spike2.y);
// ctx.lineTo(this.vertices[1].x, this.vertices[1].y);
// ctx.fillStyle = '#000'
// ctx.fill();
// },
// returnToPlayer() {
// if (Vector.magnitude(Vector.sub(this.position, m.pos)) < returnRadius) { //near player
// this.endCycle = 0;
// // if (m.energy < 0.05) {
// // m.fireCDcycle = m.cycle + 120; //fire cooldown
// // } else if (m.cycle + 15 * b.fireCDscale < m.fireCDcycle) {
// // m.fireCDcycle = m.cycle + 15 * b.fireCDscale //lower cd to 25 if it is above 25
// // }
// if (m.energy < 0.05) this.dropCaughtPowerUp()
// //recoil on catching
// const momentum = Vector.mult(Vector.sub(this.velocity, player.velocity), (m.crouch ? 0.0001 : 0.0002))
// player.force.x += momentum.x
// player.force.y += momentum.y
// // refund ammo
// b.guns[9].ammo++;
// simulation.updateGunHUD();
// // for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
// // if (b.guns[i].name === "harpoon") {
// // b.guns[i].ammo++;
// // simulation.updateGunHUD();
// // break;
// // }
// // }
// } else {
// if (m.energy > this.drain) m.energy -= this.drain
// const sub = Vector.sub(this.position, m.pos)
// const rangeScale = 1 + 0.000001 * Vector.magnitude(sub) * Vector.magnitude(sub) //return faster when far from player
// const returnForce = Vector.mult(Vector.normalise(sub), rangeScale * this.thrustMag * this.mass)
// this.force.x -= returnForce.x
// this.force.y -= returnForce.y
// this.grabPowerUp()
// }
// this.draw();
// },
// grabPowerUp() { //grab power ups near the tip of the harpoon
// if (this.caughtPowerUp) {
// Matter.Body.setPosition(this.caughtPowerUp, Vector.add(this.vertices[2], this.velocity))
// Matter.Body.setVelocity(this.caughtPowerUp, {
// x: 0,
// y: 0
// })
// } else { //&& simulation.cycle % 2
// for (let i = 0, len = powerUp.length; i < len; ++i) {
// const radius = powerUp[i].circleRadius + 50
// if (Vector.magnitudeSquared(Vector.sub(this.vertices[2], powerUp[i].position)) < radius * radius) {
// if (powerUp[i].name !== "heal" || m.health !== m.maxHealth || tech.isOverHeal) {
// this.caughtPowerUp = powerUp[i]
// Matter.Body.setVelocity(powerUp[i], {
// x: 0,
// y: 0
// })
// Matter.Body.setPosition(powerUp[i], this.vertices[2])
// powerUp[i].collisionFilter.category = 0
// powerUp[i].collisionFilter.mask = 0
// this.thrustMag *= 0.6
// this.endCycle += 0.5 //it pulls back slower, so this prevents it from ending early
// break //just pull 1 power up if possible
// }
// }
// }
// }
// },
// do() {
// if (input.fire) { //&& !Matter.Query.collides(this, body).length
// this.grabPowerUp()
// if (this.endCycle < simulation.cycle + 1) { //if at end of lifespan, but player is holding down fire, force retraction
// this.endCycle = simulation.cycle + 60
// // m.fireCDcycle = m.cycle + 120 // cool down
// this.do = this.returnToPlayer
// Matter.Body.setDensity(this, 0.0005); //reduce density on return
// if (this.angularSpeed < 0.5) this.torque += this.inertia * 0.001 * (Math.random() - 0.5) //(Math.round(Math.random()) ? 1 : -1)
// this.collisionFilter.mask = cat.map | cat.mob | cat.mobBullet | cat.mobShield // | cat.body
// }
// } else {
// //if not enough energy
// if (m.energy < 0.05) this.dropCaughtPowerUp()
// // const returnForce = Vector.mult(Vector.normalise(Vector.sub(this.position, m.pos)), 3 * this.thrustMag * this.mass)
// // this.force.x -= returnForce.x
// // this.force.y -= returnForce.y
// // this.frictionAir = 0.002
// // this.do = () => {
// // if (this.speed < 20) this.force.y += 0.0005 * this.mass;
// // }
// // } else {
// //return to player
// this.do = this.returnToPlayer
// this.endCycle = simulation.cycle + 60
// Matter.Body.setDensity(this, 0.0005); //reduce density on return
// if (this.angularSpeed < 0.5) this.torque += this.inertia * 0.001 * (Math.random() - 0.5) //(Math.round(Math.random()) ? 1 : -1)
// this.collisionFilter.mask = cat.map | cat.mob | cat.mobBullet | cat.mobShield // | cat.body
// //recoil on catching
// const momentum = Vector.mult(Vector.sub(this.velocity, player.velocity), (m.crouch ? 0.0001 : 0.0002))
// player.force.x += momentum.x
// player.force.y += momentum.y
// // }
// }
// //grappling hook
// if (input.fire && Matter.Query.collides(this, map).length) {
// Matter.Body.setPosition(this, Vector.add(this.position, {
// x: 20 * Math.cos(this.angle),
// y: 20 * Math.sin(this.angle)
// }))
// if (Matter.Query.collides(this, map).length) {
// Matter.Body.setVelocity(this, {
// x: 0,
// y: 0
// });
// Matter.Sleeping.set(this, true)
// this.endCycle = simulation.cycle + 5
// this.dropCaughtPowerUp()
// this.do = () => {
// //between player nose and the grapple
// const sub = Vector.sub(this.vertices[0], {
// x: m.pos.x + 30 * Math.cos(m.angle),
// y: m.pos.y + 30 * Math.sin(m.angle)
// })
// let dist = Vector.magnitude(sub)
// if (input.fire) {
// // m.fireCDcycle = m.cycle + 30; // cool down if out of energy
// m.fireCDcycle = m.cycle + 5 + 40 * b.fireCDscale + 60 * (m.energy < 0.05)
// this.endCycle = simulation.cycle + 10
// if (input.down) { //down
// dist = 0
// player.force.y += 5 * player.mass * simulation.g;
// }
// if (m.energy > this.drain) {
// Matter.Body.setVelocity(player, {
// x: player.velocity.x * 0.8,
// y: player.velocity.y * 0.8
// });
// const pull = Vector.mult(Vector.normalise(sub), 0.0008 * Math.min(Math.max(15, dist), 200))
// player.force.x += pull.x
// player.force.y += pull.y
// if (dist > 500) {
// m.energy -= this.drain
// if (m.energy < 0) {
// this.endCycle = 0;
// if (m.cycle + 50 < m.fireCDcycle) m.fireCDcycle = m.cycle + 50
// // refund ammo
// b.guns[9].ammo++;
// simulation.updateGunHUD();
// // for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
// // if (b.guns[i].name === "harpoon") {
// // break;
// // }
// // }
// }
// }
// }
// if (tech.isImmuneGrapple && m.immuneCycle < m.cycle + 10) {
// m.immuneCycle = m.cycle + 10;
// if (m.energy > 0.001) {
// m.energy -= 0.001
// } else { //out of energy
// Matter.Sleeping.set(this, false)
// this.collisionFilter.category = 0
// this.collisionFilter.mask = 0
// this.do = this.returnToPlayer
// this.endCycle = simulation.cycle + 60
// m.fireCDcycle = m.cycle + 120; //fire cooldown
// //recoil on catching
// const momentum = Vector.mult(Vector.sub(this.velocity, player.velocity), (m.crouch ? 0.0001 : 0.0002))
// player.force.x += momentum.x
// player.force.y += momentum.y
// }
// }
// } else {
// Matter.Sleeping.set(this, false)
// this.collisionFilter.category = 0
// this.collisionFilter.mask = 0
// this.do = this.returnToPlayer
// this.endCycle = simulation.cycle + 60
// //recoil on catching
// const momentum = Vector.mult(Vector.sub(this.velocity, player.velocity), (m.crouch ? 0.0001 : 0.0002))
// player.force.x += momentum.x
// player.force.y += momentum.y
// }
// this.draw();
// }
// }
// }
// this.force.x += this.thrustMag * this.mass * Math.cos(this.angle);
// this.force.y += this.thrustMag * this.mass * Math.sin(this.angle);
// this.draw()
// },
// });
// Composite.add(engine.world, bullet[me]); //add bullet to world
// },
harpoon(where, target, angle = m.angle, harpoonSize = 1, isReturn = false, totalCycles = 35, isReturnAmmo = true, thrust = 0.1) { harpoon(where, target, angle = m.angle, harpoonSize = 1, isReturn = false, totalCycles = 35, isReturnAmmo = true, thrust = 0.1) {
const me = bullet.length; const me = bullet.length;
const returnRadius = 100 * Math.sqrt(harpoonSize) const returnRadius = 100 * Math.sqrt(harpoonSize)
@@ -2803,16 +3123,26 @@ const b = {
if (simulation.cycle > this.lookFrequency) { if (simulation.cycle > this.lookFrequency) {
this.isArmed = true this.isArmed = true
this.lookFrequency = 55 + Math.floor(22 * Math.random()) this.lookFrequency = 55 + Math.floor(22 * Math.random())
simulation.drawList.push({ simulation.drawList.push({ x: this.position.x, y: this.position.y, radius: 10, color: "#f00", time: 4 });
x: this.position.x,
y: this.position.y,
radius: 10,
color: "#f00",
time: 4
});
this.do = function () { //overwrite the do method for this bullet this.do = function () { //overwrite the do method for this bullet
//make mobs think the mine is where the player is
// for (let i = 0; i < mob.length; i++) {
// mob[i].seePlayer.recall = mob[i].memory + Math.round(mob[i].memory * Math.random()); //cycles before mob falls a sleep
// mob[i].seePlayer.position.x = this.position.x;
// mob[i].seePlayer.position.y = this.position.y;
// mob[i].seePlayer.yes = true;
// }
this.force.y += this.mass * 0.002; //extra gravity this.force.y += this.mass * 0.002; //extra gravity
if (!(simulation.cycle % this.lookFrequency)) { //find mob targets if (!(simulation.cycle % this.lookFrequency)) { //find mob targets
const random = 300 * Math.random() const random = 300 * Math.random()
for (let i = 0, len = mob.length; i < len; ++i) { for (let i = 0, len = mob.length; i < len; ++i) {
if ( if (
@@ -2843,13 +3173,7 @@ const b = {
} }
if (this.shots < 0) this.endCycle = 0 if (this.shots < 0) this.endCycle = 0
if (!(simulation.cycle % (this.lookFrequency * 6))) { if (!(simulation.cycle % (this.lookFrequency * 6))) {
simulation.drawList.push({ simulation.drawList.push({ x: this.position.x, y: this.position.y, radius: 8, color: "#fe0", time: 4 });
x: this.position.x,
y: this.position.y,
radius: 8,
color: "#fe0",
time: 4
});
} }
} }
} }
@@ -5111,9 +5435,9 @@ const b = {
dmg: 0, //damage done in addition to the damage from momentum dmg: 0, //damage done in addition to the damage from momentum
minDmgSpeed: 2, minDmgSpeed: 2,
lookFrequency: 20 + Math.floor(7 * Math.random()) - 13 * tech.isLaserBotUpgrade, lookFrequency: 20 + Math.floor(7 * Math.random()) - 13 * tech.isLaserBotUpgrade,
range: (700 + 500 * tech.isLaserBotUpgrade) * (1 + 0.1 * Math.random()), range: (600 + 375 * tech.isLaserBotUpgrade) * (1 + 0.12 * Math.random()),
drainThreshold: 0.15 + 0.5 * Math.random() + (tech.isEnergyHealth ? 0.3 : 0),// laser bot will not attack if the player is below this energy drainThreshold: 0.15 + 0.5 * Math.random() + (tech.isEnergyHealth ? 0.3 : 0),// laser bot will not attack if the player is below this energy
drain: (0.57 - 0.45 * tech.isLaserBotUpgrade) * tech.laserDrain, drain: (0.57 - 0.43 * tech.isLaserBotUpgrade) * tech.laserDrain,
laserDamage: 0.75 + 0.75 * tech.isLaserBotUpgrade, laserDamage: 0.75 + 0.75 * tech.isLaserBotUpgrade,
endCycle: Infinity, endCycle: Infinity,
classType: "bullet", classType: "bullet",
@@ -6126,7 +6450,7 @@ const b = {
for (let i = 0; i < num; i++) { for (let i = 0; i < num; i++) {
const me = bullet.length; const me = bullet.length;
const dir = m.angle + (Math.random() - 0.5) * spread const dir = m.angle + (Math.random() - 0.5) * spread
bullet[me] = Bodies.rectangle(m.pos.x + 35 * Math.cos(m.angle) + 15 * (Math.random() - 0.5), m.pos.y + 35 * Math.sin(m.angle) + 15 * (Math.random() - 0.5), side, side, b.fireAttributes(dir)); bullet[me] = Bodies.rectangle(m.pos.x, m.pos.y, side, side, b.fireAttributes(dir));
Composite.add(engine.world, bullet[me]); //add bullet to world Composite.add(engine.world, bullet[me]); //add bullet to world
const SPEED = 52 + Math.random() * 8 const SPEED = 52 + Math.random() * 8
Matter.Body.setVelocity(bullet[me], { Matter.Body.setVelocity(bullet[me], {

View File

@@ -107,7 +107,7 @@ function collisionChecks(event) {
!mob[k].isSlowed && !mob[k].isStunned !mob[k].isSlowed && !mob[k].isStunned
) { ) {
let dmg = Math.min(Math.max(0.025 * Math.sqrt(mob[k].mass), 0.05), 0.3) * simulation.dmgScale; //player damage is capped at 0.3*dmgScale of 1.0 let dmg = Math.min(Math.max(0.025 * Math.sqrt(mob[k].mass), 0.05), 0.3) * simulation.dmgScale; //player damage is capped at 0.3*dmgScale of 1.0
if (m.isCloak) dmg *= 0.5 // if (m.isCloak) dmg *= 0.5
mob[k].foundPlayer(); mob[k].foundPlayer();
if (tech.isRewindAvoidDeath && (m.energy + 0.05) > Math.min(0.95, m.maxEnergy) && dmg > 0.01) { //CPT reversal runs in m.damage, but it stops the rest of the collision code here too if (tech.isRewindAvoidDeath && (m.energy + 0.05) > Math.min(0.95, m.maxEnergy) && dmg > 0.01) { //CPT reversal runs in m.damage, but it stops the rest of the collision code here too
m.damage(dmg); m.damage(dmg);
@@ -119,25 +119,11 @@ function collisionChecks(event) {
if (document.getElementById("tech-flip-flop")) document.getElementById("tech-flip-flop").innerHTML = ` = <strong>OFF</strong>` if (document.getElementById("tech-flip-flop")) document.getElementById("tech-flip-flop").innerHTML = ` = <strong>OFF</strong>`
m.eyeFillColor = 'transparent' m.eyeFillColor = 'transparent'
m.damage(dmg); m.damage(dmg);
if (tech.isFlipFlopCoupling) {
m.couplingChange(-5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
spawn.WIMP()
mob[mob.length - 1].isDecoupling = true //so you can find it to remove
}
} else { } else {
tech.isFlipFlopOn = true //immune to damage this hit, lose immunity for next hit tech.isFlipFlopOn = true //immune to damage this hit, lose immunity for next hit
if (document.getElementById("tech-flip-flop")) document.getElementById("tech-flip-flop").innerHTML = ` = <strong>ON</strong>` if (document.getElementById("tech-flip-flop")) document.getElementById("tech-flip-flop").innerHTML = ` = <strong>ON</strong>`
m.eyeFillColor = m.fieldMeterColor //'#0cf' m.eyeFillColor = m.fieldMeterColor //'#0cf'
if (!tech.isFlipFlopHarm) m.damage(dmg); if (!tech.isFlipFlopHarm) m.damage(dmg);
if (tech.isFlipFlopCoupling) {
m.couplingChange(5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
} }
if (tech.isFlipFlopHealth) { if (tech.isFlipFlopHealth) {
m.setMaxHealth(); m.setMaxHealth();
@@ -161,7 +147,7 @@ function collisionChecks(event) {
} }
if (tech.isPiezo) m.energy += 20.48; if (tech.isPiezo) m.energy += 20.48;
if (tech.isCouplingNoHit && m.coupling > 0) { if (tech.isCouplingNoHit && m.coupling > 0) {
m.couplingChange(-0.5) m.couplingChange(-5)
const unit = Vector.rotate({ x: 1, y: 0 }, 6.28 * Math.random()) const unit = Vector.rotate({ x: 1, y: 0 }, 6.28 * Math.random())
let where = Vector.add(m.pos, Vector.mult(unit, 17)) let where = Vector.add(m.pos, Vector.mult(unit, 17))
@@ -295,7 +281,7 @@ function collisionChecks(event) {
} }
} }
let dmg = tech.blockDamage * m.dmgScale * v * obj.mass * (tech.isMobBlockFling ? 2.5 : 1) * (tech.isBlockRestitution ? 2.5 : 1) * ((m.fieldMode === 0 || m.fieldMode === 8) ? 1 + 0.4 * m.coupling : 1); let dmg = tech.blockDamage * m.dmgScale * v * obj.mass * (tech.isMobBlockFling ? 2.5 : 1) * (tech.isBlockRestitution ? 2.5 : 1) * ((m.fieldMode === 0 || m.fieldMode === 8) ? 1 + 0.04 * m.coupling : 1);
if (mob[k].isShielded) dmg *= 0.7 if (mob[k].isShielded) dmg *= 0.7
mob[k].damage(dmg, true); mob[k].damage(dmg, true);

View File

@@ -302,6 +302,32 @@ const build = {
document.getElementById("hide-images").checked = localSettings.isHideImages document.getElementById("hide-images").checked = localSettings.isHideImages
// console.log(localSettings.isHideImages, from) // console.log(localSettings.isHideImages, from)
}, },
hideHUD() {
localSettings.isHideHUD = !localSettings.isHideHUD
if (localSettings.isAllowed) localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage
document.getElementById("hide-hud").checked = localSettings.isHideHUD
document.getElementById("hide-hud").classList.toggle("ticked")
simulation.removeEphemera("dmgDefBars")
if (!localSettings.isHideHUD) {
simulation.ephemera.push({
name: "dmgDefBars", count: 0, do() {
if (!(m.cycle % 15)) { //4 times a second
const defense = m.defense() //update defense bar
if (m.lastCalculatedDefense !== defense) {
document.getElementById("defense-bar").style.width = Math.floor(300 * m.maxHealth * (1 - defense)) + "px";
m.lastCalculatedDefense = defense
}
const damage = tech.damageFromTech() //update damage bar
if (m.lastCalculatedDamage !== damage) {
document.getElementById("damage-bar").style.height = Math.floor((Math.atan(0.25 * damage - 0.25) + 0.25) * 0.53 * canvas.height) + "px";
m.lastCalculatedDamage = damage
}
}
},
})
}
},
pauseGrid() { pauseGrid() {
// build.pixelDraw(); // build.pixelDraw();
//used for junk estimation //used for junk estimation
@@ -330,15 +356,18 @@ const build = {
<g stroke='none' fill='#333' stroke-width="2" font-size="14px" font-family="Ariel, sans-serif"> <text x="5" y="15">copy build url</text></g> <g stroke='none' fill='#333' stroke-width="2" font-size="14px" font-family="Ariel, sans-serif"> <text x="5" y="15">copy build url</text></g>
</svg><span style="font-size:1.5em;font-weight: 600; float: right;">PAUSED</span> </svg><span style="font-size:1.5em;font-weight: 600; float: right;">PAUSED</span>
<br> <br>
<label for="hide-images-pause" title="hide images for fields, guns, and tech" style="font-size:1.3em;" >hide images:</label>
<input onclick="build.showImages('pause')" type="checkbox" id="hide-images-pause" name="hide-images-pause" ${localSettings.isHideImages ? "checked" : ""}> <input onclick="build.showImages('pause')" type="checkbox" id="hide-images-pause" name="hide-images-pause" ${localSettings.isHideImages ? "checked" : ""}>
<label for="hide-images-pause" title="hide images for fields, guns, and tech" style="font-size:1.3em;" >hide images</label>
<span style="float: right;">press ${input.key.pause} to resume</span> <span style="float: right;">press ${input.key.pause} to resume</span>
<br> <br>
<input onclick="build.hideHUD('settings')" type="checkbox" id="hide-hud" name="hide-hud" ${localSettings.isHideHUD ? "checked" : ""}>
<label for="hide-hud" title="hide: tech, defense, damage, in game console" style="font-size:1.3em;">minimal HUD</label>
<br>
<br><strong class='color-d'>damage</strong>: ${((tech.damageFromTech())).toPrecision(4)} &nbsp; &nbsp; difficulty: ${((m.dmgScale)).toPrecision(4)} <br><strong class='color-d'>damage</strong>: ${((tech.damageFromTech())).toPrecision(4)} &nbsp; &nbsp; difficulty: ${((m.dmgScale)).toPrecision(4)}
<br><strong class='color-defense'>defense</strong>: ${tech.isEnergyHealth ? (1 - Math.pow(m.defense(), 0.13)).toPrecision(5) : (1 - m.defense()).toPrecision(5)} &nbsp; &nbsp; difficulty: ${(1 / simulation.dmgScale).toPrecision(4)} <br><strong class='color-defense'>defense</strong>: ${tech.isEnergyHealth ? (1 - Math.pow(m.defense(), 0.13)).toPrecision(5) : (1 - m.defense()).toPrecision(5)} &nbsp; &nbsp; difficulty: ${(1 / simulation.dmgScale).toPrecision(4)}
<br><strong><em>fire rate</em></strong>: ${((1 - b.fireCDscale) * 100).toFixed(b.fireCDscale < 0.1 ? 2 : 0)}% <br><strong><em>fire rate</em></strong>: ${((1 - b.fireCDscale) * 100).toFixed(b.fireCDscale < 0.1 ? 2 : 0)}%
${tech.duplicationChance() ? `<br><strong class='color-dup'>duplication</strong>: ${(tech.duplicationChance() * 100).toFixed(0)}%` : ""} ${tech.duplicationChance() ? `<br><strong class='color-dup'>duplication</strong>: ${(tech.duplicationChance() * 100).toFixed(0)}%` : ""}
${m.coupling ? `<br><strong class='color-coupling'>coupling</strong>: ${(m.coupling).toFixed(2)} &nbsp; <span style = 'font-size:90%;'>` + m.couplingDescription() + "</span>" : ""} ${m.coupling ? `<br><span style = 'font-size:90%;'>` + m.couplingDescription(m.coupling) + `</span> from ${(m.coupling).toFixed(0)} ${powerUps.orb.coupling(1)}` : ""}
${botText} ${botText}
<br> <br>
<br><strong class='color-h'>health</strong>: (${(m.health * 100).toFixed(0)} / ${(m.maxHealth * 100).toFixed(0)}) <br><strong class='color-h'>health</strong>: (${(m.health * 100).toFixed(0)} / ${(m.maxHealth * 100).toFixed(0)})
@@ -380,7 +409,7 @@ ${simulation.isCheating ? "<br><br><em>lore disabled</em>" : ""}
<div class="grid-title"><div class="circle-grid gun"></div> &nbsp; ${build.nameLink(b.guns[b.inventory[i]].name)} - <span style="font-size:100%;font-weight: 100;">${b.guns[b.inventory[i]].ammo}</span></div> <div class="grid-title"><div class="circle-grid gun"></div> &nbsp; ${build.nameLink(b.guns[b.inventory[i]].name)} - <span style="font-size:100%;font-weight: 100;">${b.guns[b.inventory[i]].ammo}</span></div>
${b.guns[b.inventory[i]].description}</div> </div>` ${b.guns[b.inventory[i]].description}</div> </div>`
} }
text += `<div class="pause-grid-module pause-console" style = "background-color: rgba(255,255,255,0.3);">${document.getElementById("text-log").innerHTML}</div>` //show last in game console message if (!localSettings.isHideHUD) text += `<div class="pause-grid-module pause-console" style = "background-color: rgba(255,255,255,0.3);">${document.getElementById("text-log").innerHTML}</div>` //show last in game console message
let el = document.getElementById("pause-grid-left") let el = document.getElementById("pause-grid-left")
el.style.display = "grid" el.style.display = "grid"
el.innerHTML = text el.innerHTML = text
@@ -432,7 +461,7 @@ ${simulation.isCheating ? "<br><br><em>lore disabled</em>" : ""}
text += build.techText(i) + "</div>" text += build.techText(i) + "</div>"
} }
} else if (tech.tech[i].isLost) { } else if (tech.tech[i].isLost) {
text += `<div class="pause-grid-module" style="text-decoration: line-through;"><div class="grid-title">${tech.tech[i].link}</div>${tech.tech[i].descriptionFunction ? tech.tech[i].descriptionFunction() : tech.tech[i].description}</div></div>` text += `<div class="pause-grid-module" style="text-decoration: line-through; padding-left: 8px; opacity: 0.4;"><div class="grid-title">${tech.tech[i].link}</div>${tech.tech[i].descriptionFunction ? tech.tech[i].descriptionFunction() : tech.tech[i].description}</div></div>`
} }
} }
el = document.getElementById("pause-grid-right") el = document.getElementById("pause-grid-right")
@@ -454,7 +483,6 @@ ${simulation.isCheating ? "<br><br><em>lore disabled</em>" : ""}
}, },
unPauseGrid() { unPauseGrid() {
document.getElementById("tech").style.display = "inline"
document.getElementById("guns").style.display = "inline" document.getElementById("guns").style.display = "inline"
document.getElementById("field").style.display = "inline" document.getElementById("field").style.display = "inline"
if (tech.isEnergyHealth) { if (tech.isEnergyHealth) {
@@ -464,8 +492,11 @@ ${simulation.isCheating ? "<br><br><em>lore disabled</em>" : ""}
document.getElementById("health").style.display = "inline" document.getElementById("health").style.display = "inline"
document.getElementById("health-bg").style.display = "inline" document.getElementById("health-bg").style.display = "inline"
} }
document.getElementById("defense-bar").style.display = "inline" if (!localSettings.isHideHUD) {
document.getElementById("damage-bar").style.display = "inline" document.getElementById("tech").style.display = "inline"
document.getElementById("defense-bar").style.display = "inline"
document.getElementById("damage-bar").style.display = "inline"
}
// document.body.style.overflow = "hidden" // document.body.style.overflow = "hidden"
document.getElementById("pause-grid-left").style.display = "none" document.getElementById("pause-grid-left").style.display = "none"
document.getElementById("pause-grid-right").style.display = "none" document.getElementById("pause-grid-right").style.display = "none"
@@ -1494,6 +1525,10 @@ if (localSettings.isAllowed && !localSettings.isEmpty) {
} }
if (localSettings.isHideImages === undefined) localSettings.isHideImages = true //default to hide images if (localSettings.isHideImages === undefined) localSettings.isHideImages = true //default to hide images
document.getElementById("hide-images").checked = localSettings.isHideImages document.getElementById("hide-images").checked = localSettings.isHideImages
if (localSettings.isHideHUD === undefined) localSettings.isHideHUD = false
document.getElementById("hide-hud").checked = localSettings.isHideHUD
} else { } else {
console.log('setting default localSettings') console.log('setting default localSettings')
const isAllowed = localSettings.isAllowed //don't overwrite isAllowed value const isAllowed = localSettings.isAllowed //don't overwrite isAllowed value
@@ -1513,6 +1548,7 @@ if (localSettings.isAllowed && !localSettings.isEmpty) {
isHuman: false, isHuman: false,
key: undefined, key: undefined,
isHideImages: true, //default to hide images isHideImages: true, //default to hide images
isHideHUD: false,
}; };
input.setDefault() input.setDefault()
if (localSettings.isAllowed) localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage if (localSettings.isAllowed) localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage

View File

@@ -26,31 +26,31 @@ const level = {
// powerUps.research.changeRerolls(11) // powerUps.research.changeRerolls(11)
// m.immuneCycle = Infinity //you can't take damage // m.immuneCycle = Infinity //you can't take damage
// tech.tech[297].frequency = 100 // tech.tech[297].frequency = 100
// m.couplingChange(5) // m.couplingChange(10)
// m.setField("standing wave") //1 standing wave 2 perfect diamagnetism 3 negative mass 4 molecular assembler 5 plasma torch 6 time dilation 7 metamaterial cloaking 8 pilot wave 9 wormhole // m.setField("metamaterial cloaking") //1 standing wave 2 perfect diamagnetism 3 negative mass 4 molecular assembler 5 plasma torch 6 time dilation 7 metamaterial cloaking 8 pilot wave 9 wormhole
// m.energy = 0 // m.energy = 0
// simulation.molecularMode = 2 // simulation.molecularMode = 2
// m.damage(0.1); // m.damage(0.1);
// b.giveGuns("harpoon") //0 nail gun 1 shotgun 2 super balls 3 wave 4 missiles 5 grenades 6 spores 7 drones 8 foam 9 harpoon 10 mine 11 laser // b.giveGuns("harpoon") //0 nail gun 1 shotgun 2 super balls 3 wave 4 missiles 5 grenades 6 spores 7 drones 8 foam 9 harpoon 10 mine 11 laser
// b.giveGuns("foam") //0 nail gun 1 shotgun 2 super balls 3 wave 4 missiles 5 grenades 6 spores 7 drones 8 foam 9 harpoon 10 mine 11 laser // b.giveGuns("shotgun") //0 nail gun 1 shotgun 2 super balls 3 wave 4 missiles 5 grenades 6 spores 7 drones 8 foam 9 harpoon 10 mine 11 laser
// b.guns[3].ammo = 100000000 // b.guns[3].ammo = 100000000
// tech.giveTech("induction brake") // tech.giveTech("grappling hook")
// tech.giveTech("null hypothesis") // tech.giveTech("null hypothesis")
// for (let i = 0; i < 1; ++i) tech.giveTech("dye laser")
// for (let i = 0; i < 1; ++i) tech.giveTech("free-electron laser") // for (let i = 0; i < 1; ++i) tech.giveTech("free-electron laser")
// for (let i = 0; i < 1; ++i) tech.giveTech("waste heat recovery") // for (let i = 0; i < 1; ++i) tech.giveTech("waste heat recovery")
// requestAnimationFrame(() => { for (let i = 0; i < 1; i++) tech.giveTech("foam-bot") }); // requestAnimationFrame(() => { for (let i = 0; i < 1; i++) tech.giveTech("foam-bot") });
// for (let i = 0; i < 1; i++) tech.giveTech("foam-bot upgrade") // for (let i = 0; i < 1; i++) tech.giveTech("foam-bot upgrade")
// for (let i = 0; i < 1; ++i) tech.giveTech("Occams razor")
// for (let i = 0; i < 3; i++) powerUps.directSpawn(450, -50, "tech"); // for (let i = 0; i < 3; i++) powerUps.directSpawn(450, -50, "tech");
// for (let i = 0; i < 10; i++) powerUps.directSpawn(1750, -500, "research"); // for (let i = 0; i < 10; i++) powerUps.directSpawn(1750, -500, "research");
// for (let i = 0; i < 10; i++) powerUps.directSpawn(1750, -500, "coupling"); // for (let i = 0; i < 10; i++) powerUps.directSpawn(1750, -500, "coupling");
// level.superNgonBros(); // level.testing();
// spawn.nodeGroup(3200, -300, "sniper") // spawn.nodeGroup(3200, -300, "sniper")
// spawn.nodeGroup(2200, -300, "sniper") // spawn.nodeGroup(2200, -300, "sniper")
// spawn.nodeGroup(2200, -300, "sniper") // spawn.nodeGroup(2200, -300, "sniper")
// spawn.mantisBoss(1900, -500) // spawn.mantisBoss(1900, -500)
// spawn.cellBoss(1900, -500) // spawn.cellBoss(1900, -500)
// for (let i = 0; i < 5; ++i) spawn.starter(1900, -500, 50) // for (let i = 0; i < 2; ++i) spawn.starter(1900, -500, 50)
// spawn.sneaker(1900, -500, 25) // spawn.sneaker(1900, -500, 25)
// spawn.sniper(2000, -450) // spawn.sniper(2000, -450)
// spawn.zombie(1000 + 1000 * Math.random(), -500 + 300 * Math.random(), 30, 5, "white") // zombie(x, y, radius, sides, color) // spawn.zombie(1000 + 1000 * Math.random(), -500 + 300 * Math.random(), 30, 5, "white") // zombie(x, y, radius, sides, color)
@@ -139,12 +139,6 @@ const level = {
tech.isFlipFlopOn = true tech.isFlipFlopOn = true
if (tech.isFlipFlopHealth) m.setMaxHealth() if (tech.isFlipFlopHealth) m.setMaxHealth()
if (tech.isRelayEnergy) m.setMaxEnergy() if (tech.isRelayEnergy) m.setMaxEnergy()
if (tech.isFlipFlopCoupling) {
m.couplingChange(5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
m.eyeFillColor = m.fieldMeterColor m.eyeFillColor = m.fieldMeterColor
simulation.makeTextLog(`tech.isFlipFlopOn <span class='color-symbol'>=</span> true`); simulation.makeTextLog(`tech.isFlipFlopOn <span class='color-symbol'>=</span> true`);
} }
@@ -1192,7 +1186,7 @@ const level = {
y = y + height / 2 y = y + height / 2
const doorBlock = body[body.length] = Bodies.rectangle(x, y, width, height, { const doorBlock = body[body.length] = Bodies.rectangle(x, y, width, height, {
collisionFilter: { collisionFilter: {
category: cat.map, category: cat.body,//cat.map,
mask: cat.player | cat.body | cat.bullet | cat.powerUp | cat.mob | cat.mobBullet //cat.player | cat.map | cat.body | cat.bullet | cat.powerUp | cat.mob | cat.mobBullet mask: cat.player | cat.body | cat.bullet | cat.powerUp | cat.mob | cat.mobBullet //cat.player | cat.map | cat.body | cat.bullet | cat.powerUp | cat.mob | cat.mobBullet
}, },
isNoSetCollision: true, isNoSetCollision: true,
@@ -1252,7 +1246,7 @@ const level = {
return this.position.y > y - 1 return this.position.y > y - 1
}, },
draw() { draw() {
ctx.fillStyle = "#555" ctx.fillStyle = "#666"
ctx.beginPath(); ctx.beginPath();
const v = this.vertices; const v = this.vertices;
ctx.moveTo(v[0].x, v[0].y); ctx.moveTo(v[0].x, v[0].y);
@@ -3175,6 +3169,8 @@ const level = {
const doorIn = level.door(-313, -950, 525, 200, 190, 2) //x, y, width, height, distance, speed = 1 const doorIn = level.door(-313, -950, 525, 200, 190, 2) //x, y, width, height, distance, speed = 1
const doorOut = level.door(2762, -175, 525, 200, 190, 2) //x, y, width, height, distance, speed = 1 const doorOut = level.door(2762, -175, 525, 200, 190, 2) //x, y, width, height, distance, speed = 1
doorIn.collisionFilter.category = cat.map;
doorOut.collisionFilter.category = cat.map; // to prevent boson composite from letting the player skip the level
// doorOut.isClosing = true // doorOut.isClosing = true
let isDoorsLocked = false let isDoorsLocked = false
let isFightOver = false let isFightOver = false
@@ -5186,6 +5182,10 @@ const level = {
portal[3].query() portal[3].query()
}; };
level.customTopLayer = () => { level.customTopLayer = () => {
doorButtonRight.draw();
doorCenterRight.draw();
doorCenterLeft.draw();
doorLeft.draw();
hazardSlimeLeft.query(); hazardSlimeLeft.query();
hazardSlimeRight.query(); hazardSlimeRight.query();
portal[0].draw(); portal[0].draw();
@@ -22147,8 +22147,10 @@ const level = {
m.addHealth(0.25) m.addHealth(0.25)
document.getElementById("health").style.display = "inline" //show your health bar document.getElementById("health").style.display = "inline" //show your health bar
document.getElementById("health-bg").style.display = "inline" document.getElementById("health-bg").style.display = "inline"
document.getElementById("defense-bar").style.display = "inline" if (!localSettings.isHideHUD) {
document.getElementById("damage-bar").style.display = "inline" document.getElementById("defense-bar").style.display = "inline"
document.getElementById("damage-bar").style.display = "inline"
}
level.setPosToSpawn(60, -50); //normal spawn level.setPosToSpawn(60, -50); //normal spawn
spawn.mapRect(10, -10, 100, 20); //small platform for player spawn.mapRect(10, -10, 100, 20); //small platform for player
level.exit.x = 1775; level.exit.x = 1775;

View File

@@ -239,7 +239,7 @@ const mobs = {
deathCount: 0, deathCount: 0,
mobSpawnWithHealth: 1, mobSpawnWithHealth: 1,
setMobSpawnHealth() { setMobSpawnHealth() {
mobs.mobSpawnWithHealth = 0.88 ** (tech.mobSpawnWithHealth) //+ (m.fieldMode === 0 || m.fieldMode === 7) * m.coupling mobs.mobSpawnWithHealth = 0.88 ** (tech.mobSpawnWithHealth)
}, },
//********************************************************************************************** //**********************************************************************************************
//********************************************************************************************** //**********************************************************************************************
@@ -337,7 +337,7 @@ const mobs = {
}, },
alwaysSeePlayer() { alwaysSeePlayer() {
if (!m.isCloak) { if (!m.isCloak) {
this.seePlayer.recall = true; this.seePlayer.recall = 1;
this.seePlayer.position.x = player.position.x; this.seePlayer.position.x = player.position.x;
this.seePlayer.position.y = player.position.y; this.seePlayer.position.y = player.position.y;
} }
@@ -1228,15 +1228,6 @@ const mobs = {
simulation.timePlayerSkip((this.isBoss ? 45 : 25) * tech.deathSkipTime) simulation.timePlayerSkip((this.isBoss ? 45 : 25) * tech.deathSkipTime)
simulation.loop(); //ending with a wipe and normal loop fixes some very minor graphical issues where things are draw in the wrong locations simulation.loop(); //ending with a wipe and normal loop fixes some very minor graphical issues where things are draw in the wrong locations
}); //wrapping in animation frame prevents errors, probably }); //wrapping in animation frame prevents errors, probably
// if (tech.isFlipFlopOn) {
// m.rewind(this.isBoss ? 45 : 25)
// } else {
// requestAnimationFrame(() => {
// simulation.timePlayerSkip(this.isBoss ? 45 : 25)
// simulation.loop(); //ending with a wipe and normal loop fixes some very minor graphical issues where things are draw in the wrong locations
// }); //wrapping in animation frame prevents errors, probably
// }
} }
if (tech.isEnergyLoss) m.energy *= 0.8; if (tech.isEnergyLoss) m.energy *= 0.8;
powerUps.spawnRandomPowerUp(this.position.x, this.position.y); powerUps.spawnRandomPowerUp(this.position.x, this.position.y);

View File

@@ -525,7 +525,7 @@ const m = {
}, },
baseHealth: 1, baseHealth: 1,
setMaxHealth() { setMaxHealth() {
m.maxHealth = m.baseHealth + tech.extraMaxHealth + 2.22 * tech.isFallingDamage + 4 * tech.isFlipFlop * tech.isFlipFlopOn * tech.isFlipFlopHealth //+ (m.fieldMode === 0 || m.fieldMode === 5) * 0.5 * m.coupling m.maxHealth = m.baseHealth + tech.extraMaxHealth + 2.22 * tech.isFallingDamage + 4 * tech.isFlipFlop * tech.isFlipFlopOn * tech.isFlipFlopHealth
document.getElementById("health-bg").style.width = `${Math.floor(300 * m.maxHealth)}px` document.getElementById("health-bg").style.width = `${Math.floor(300 * m.maxHealth)}px`
simulation.makeTextLog(`<span class='color-var'>m</span>.<span class='color-h'>maxHealth</span> <span class='color-symbol'>=</span> ${m.maxHealth.toFixed(2)}`) simulation.makeTextLog(`<span class='color-var'>m</span>.<span class='color-h'>maxHealth</span> <span class='color-symbol'>=</span> ${m.maxHealth.toFixed(2)}`)
if (m.health > m.maxHealth) m.health = m.maxHealth; if (m.health > m.maxHealth) m.health = m.maxHealth;
@@ -549,7 +549,7 @@ const m = {
if (tech.isSlowFPS) dmg *= 0.8 if (tech.isSlowFPS) dmg *= 0.8
if (tech.energyRegen === 0) dmg *= 0.34 if (tech.energyRegen === 0) dmg *= 0.34
// if (tech.healthDrain) dmg *= 1 + 3.33 * tech.healthDrain //tech.healthDrain = 0.03 at one stack //cause more damage // if (tech.healthDrain) dmg *= 1 + 3.33 * tech.healthDrain //tech.healthDrain = 0.03 at one stack //cause more damage
if (m.fieldMode === 0 || m.fieldMode === 3) dmg *= 0.73 ** m.coupling if (m.fieldMode === 0 || m.fieldMode === 3) dmg *= 0.73 ** (0.1 * m.coupling)
if (tech.isLowHealthDefense) dmg *= 1 - Math.max(0, 1 - m.health) * 0.8 if (tech.isLowHealthDefense) dmg *= 1 - Math.max(0, 1 - m.health) * 0.8
if (tech.isHarmReduceNoKill && m.lastKillCycle + 300 < m.cycle) dmg *= 0.33 if (tech.isHarmReduceNoKill && m.lastKillCycle + 300 < m.cycle) dmg *= 0.33
if (tech.squirrelFx !== 1) dmg *= Math.pow(0.7, (tech.squirrelFx - 1) / 0.4) //cause more damage if (tech.squirrelFx !== 1) dmg *= Math.pow(0.7, (tech.squirrelFx - 1) / 0.4) //cause more damage
@@ -1893,7 +1893,7 @@ const m = {
} }
}, },
setMaxEnergy(isMessage = true) { setMaxEnergy(isMessage = true) {
m.maxEnergy = (tech.isMaxEnergyTech ? 0.5 : 1) + tech.bonusEnergy + tech.healMaxEnergyBonus + tech.harmonicEnergy + 2 * tech.isGroundState + 3 * tech.isRelay * tech.isFlipFlopOn * tech.isRelayEnergy + 1.5 * (m.fieldMode === 1) + (m.fieldMode === 0 || m.fieldMode === 1) * 0.5 * m.coupling + 0.4 * tech.isStandingWaveExpand m.maxEnergy = (tech.isMaxEnergyTech ? 0.5 : 1) + tech.bonusEnergy + tech.healMaxEnergyBonus + tech.harmonicEnergy + 2 * tech.isGroundState + 3 * tech.isRelay * tech.isFlipFlopOn * tech.isRelayEnergy + 1.5 * (m.fieldMode === 1) + (m.fieldMode === 0 || m.fieldMode === 1) * 0.05 * m.coupling + 0.4 * tech.isStandingWaveExpand
if (isMessage) simulation.makeTextLog(`<span class='color-var'>m</span>.<span class='color-f'>maxEnergy</span> <span class='color-symbol'>=</span> ${(m.maxEnergy.toFixed(2))}`) if (isMessage) simulation.makeTextLog(`<span class='color-var'>m</span>.<span class='color-f'>maxEnergy</span> <span class='color-symbol'>=</span> ${(m.maxEnergy.toFixed(2))}`)
}, },
fieldMeterColor: "#0cf", fieldMeterColor: "#0cf",
@@ -1945,7 +1945,7 @@ const m = {
} else { } else {
m.fieldRegen = 0.001 //6 energy per second m.fieldRegen = 0.001 //6 energy per second
} }
if (m.fieldMode === 0 || m.fieldMode === 4) m.fieldRegen += 0.00133 * m.coupling //return `generate <strong>${(6*couple).toFixed(0)}</strong> <strong class='color-f'>energy</strong> per second` if (m.fieldMode === 0 || m.fieldMode === 4) m.fieldRegen += 0.000133 * m.coupling //return `generate <strong>${(6*couple).toFixed(0)}</strong> <strong class='color-f'>energy</strong> per second`
if (tech.isTimeCrystals) { if (tech.isTimeCrystals) {
m.fieldRegen *= 2.5 m.fieldRegen *= 2.5
} else if (tech.isGroundState) { } else if (tech.isGroundState) {
@@ -2290,7 +2290,7 @@ const m = {
} }
if (!who.isInvulnerable && (m.coupling && m.fieldMode === 0) && bullet.length < 200) { //for field emitter iceIX if (!who.isInvulnerable && (m.coupling && m.fieldMode === 0) && bullet.length < 200) { //for field emitter iceIX
for (let i = 0; i < m.coupling; i++) { for (let i = 0; i < m.coupling; i++) {
if (m.coupling - i > 1.25 * Math.random()) { if (0.1 * m.coupling - i > 1.25 * Math.random()) {
const sub = Vector.mult(Vector.normalise(Vector.sub(who.position, m.pos)), (m.fieldRange * m.harmonicRadius) * (0.4 + 0.3 * Math.random())) //m.harmonicRadius should be 1 unless you are standing wave expansion const sub = Vector.mult(Vector.normalise(Vector.sub(who.position, m.pos)), (m.fieldRange * m.harmonicRadius) * (0.4 + 0.3 * Math.random())) //m.harmonicRadius should be 1 unless you are standing wave expansion
const rad = Vector.rotate(sub, 1 * (Math.random() - 0.5)) const rad = Vector.rotate(sub, 1 * (Math.random() - 0.5))
const angle = Math.atan2(sub.y, sub.x) const angle = Math.atan2(sub.y, sub.x)
@@ -2457,28 +2457,27 @@ const m = {
couplingDescription(couple = m.coupling) { couplingDescription(couple = m.coupling) {
switch (m.fieldMode) { switch (m.fieldMode) {
case 0: //field emitter case 0: //field emitter
return `gain the <strong class='color-coupling'>coupling</strong> effects of <strong>all</strong> <strong class='color-f'>fields</strong>` return `<strong>all</strong> other <strong class='color-f'>field</strong> effects`
case 1: //standing wave case 1: //standing wave
// return `<span style = 'font-size:95%;'><strong>deflecting</strong> condenses +${couple.toFixed(1)} <strong class='color-s'>ice IX</strong></span>` // return `<span style = 'font-size:95%;'><strong>deflecting</strong> condenses +${couple.toFixed(1)} <strong class='color-s'>ice IX</strong></span>`
// return `<span style = 'font-size:95%;'><strong>deflecting</strong> condenses +${couple.toFixed(1)} <strong class='color-s'>ice IX</strong></span>` return `+${(couple * 5).toFixed(0)} maximum <strong class='color-f'>energy</strong>`
return `+${(couple * 50).toFixed(0)} maximum <strong class='color-f'>energy</strong>`
case 2: //perfect diamagnetism case 2: //perfect diamagnetism
return `<span style = 'font-size:95%;'><strong>deflecting</strong> condenses +${couple.toFixed(1)} <strong class='color-s'>ice IX</strong></span>` return `<span style = 'font-size:95%;'><strong>deflecting</strong> condenses ${0.1 * couple.toFixed(2)} <strong class='color-s'>ice IX</strong></span>`
// return `<span style = 'font-size:89%;'><strong>invulnerable</strong> <strong>+${2*couple}</strong> seconds post collision</span>` // return `<span style = 'font-size:89%;'><strong>invulnerable</strong> <strong>+${2*couple}</strong> seconds post collision</span>`
case 3: //negative mass case 3: //negative mass
return `<strong>+${((1 - 0.73 ** couple) * 100).toFixed(1)}%</strong> <strong class='color-defense'>defense</strong>` return `<strong>+${((1 - 0.73 ** couple) * 10).toFixed(1)}%</strong> <strong class='color-defense'>defense</strong>`
case 4: //assembler case 4: //assembler
return `generate <strong>${(8 * couple).toFixed(0)}</strong> <strong class='color-f'>energy</strong> per second` return `generate <strong>${(0.8 * couple).toFixed(1)}</strong> <strong class='color-f'>energy</strong> per second`
case 5: //plasma case 5: //plasma
return `<strong>+${(15 * couple).toFixed(0)}%</strong> <strong class='color-d'>damage</strong>` return `<strong>+${(1.5 * couple).toFixed(1)}%</strong> <strong class='color-d'>damage</strong>`
case 6: //time dilation case 6: //time dilation
return `<strong>+${(50 * couple).toFixed(0)}%</strong> longer <strong style='letter-spacing: 2px;'>stopped time</strong>` //<strong>movement</strong>, <strong>jumping</strong>, and return `<strong>+${(5 * couple).toFixed(0)}%</strong> longer <strong style='letter-spacing: 2px;'>stopped time</strong>` //<strong>movement</strong>, <strong>jumping</strong>, and
case 7: //cloaking case 7: //cloaking
return `<strong>+${(33 * couple).toFixed(0)}%</strong> ambush <strong class='color-d'>damage</strong>` return `<strong>+${(3.3 * couple).toFixed(1)}%</strong> ambush <strong class='color-d'>damage</strong>`
case 8: //pilot wave case 8: //pilot wave
return `<strong>+${(40 * couple).toFixed(0)}%</strong> <strong class='color-block'>block</strong> collision <strong class='color-d'>damage</strong>` return `<strong>+${(4 * couple).toFixed(0)}%</strong> <strong class='color-block'>block</strong> collision <strong class='color-d'>damage</strong>`
case 9: //wormhole case 9: //wormhole
return `<span style = 'font-size:89%;'>after eating <strong class='color-block'>blocks</strong> <strong>+${(20 * couple).toFixed(0)}</strong> <strong class='color-f'>energy</strong></span>` return `<span style = 'font-size:89%;'>after eating <strong class='color-block'>blocks</strong> <strong>+${(2 * couple).toFixed(0)}</strong> <strong class='color-f'>energy</strong></span>`
} }
}, },
couplingChange(change = 0) { couplingChange(change = 0) {
@@ -2490,11 +2489,10 @@ const m = {
if (powerUp[i].name === "coupling") { if (powerUp[i].name === "coupling") {
Matter.Composite.remove(engine.world, powerUp[i]); Matter.Composite.remove(engine.world, powerUp[i]);
powerUp.splice(i, 1); powerUp.splice(i, 1);
m.coupling += 0.1 m.coupling += 1
if (!(m.coupling < 0)) break if (!(m.coupling < 0)) break
} }
} }
m.coupling = 0 //can't go negative m.coupling = 0 //can't go negative
} }
m.setMaxEnergy(false); m.setMaxEnergy(false);
@@ -2503,33 +2501,7 @@ const m = {
mobs.setMobSpawnHealth(); mobs.setMobSpawnHealth();
powerUps.setPowerUpMode(); powerUps.setPowerUpMode();
if ((m.fieldMode === 0 || m.fieldMode === 9) && !build.isExperimentSelection && !simulation.isTextLogOpen) simulation.circleFlare(0.4); // if ((m.fieldMode === 0 || m.fieldMode === 9) && !build.isExperimentSelection && !simulation.isTextLogOpen) simulation.circleFlare(0.4);
// m.collisionImmuneCycles = 30 + m.coupling * 120 //2 seconds
// switch (m.fieldMode) {
// case 0: //field emitter
// // m.fieldFireRate = 0.8 ** (m.coupling)
// // b.setFireCD();
// break
// // case 1: //standing wave
// // break
// // case 2: //perfect diamagnetism
// // break
// // case 3: //negative mass
// // break
// // case 4: //assembler
// // break
// // case 5: //plasma
// // break
// case 6: //time dilation
// // m.fieldFireRate = 0.75 * 0.8 ** (m.coupling)
// break
// // case 7: //cloaking
// // break
// // case 8: //pilot wave
// // break
// // case 9: //wormhole
// // break
// }
}, },
setField(index) { setField(index) {
if (isNaN(index)) { //find index by name if (isNaN(index)) { //find index by name
@@ -2577,6 +2549,12 @@ const m = {
} }
} }
}, },
// <div id="cube" style="width: 4em; height: 8em;">
// <div style="transform: translate3d(1em, 0em, 0em)">1</div>
// <div style="transform: translate3d(2em, 0em, 0em)">2</div>
// <div style="transform: translate3d(3em, 0em, 0em)">3</div>
// <div style="transform: translate3d(4em, 0em, 0em)">4</div>
// </div>
{ {
name: "standing wave", name: "standing wave",
//<strong>deflecting</strong> protects you in every <strong>direction</strong> //<strong>deflecting</strong> protects you in every <strong>direction</strong>
@@ -2586,7 +2564,7 @@ const m = {
drainCD: 0, drainCD: 0,
effect: () => { effect: () => {
m.fieldBlockCD = 0; m.fieldBlockCD = 0;
m.blockingRecoil = 2 //4 is normal m.blockingRecoil = 1.5 //4 is normal
m.fieldRange = 185 m.fieldRange = 185
m.fieldShieldingScale = 1.6 * Math.pow(0.5, (tech.harmonics - 2)) m.fieldShieldingScale = 1.6 * Math.pow(0.5, (tech.harmonics - 2))
// m.fieldHarmReduction = 0.66; //33% reduction // m.fieldHarmReduction = 0.66; //33% reduction
@@ -2717,7 +2695,7 @@ const m = {
m.fieldCDcycle = m.cycle + m.fieldBlockCD + (mob[i].isShielded ? 10 : 0); m.fieldCDcycle = m.cycle + m.fieldBlockCD + (mob[i].isShielded ? 10 : 0);
if (!mob[i].isInvulnerable && bullet.length < 250) { if (!mob[i].isInvulnerable && bullet.length < 250) {
for (let i = 0; i < m.coupling; i++) { for (let i = 0; i < m.coupling; i++) {
if (m.coupling - i > Math.random()) { if (0.1 * m.coupling - i > Math.random()) {
const angle = m.fieldAngle + 4 * m.fieldArc * (Math.random() - 0.5) const angle = m.fieldAngle + 4 * m.fieldArc * (Math.random() - 0.5)
const radius = m.fieldRange * (0.6 + 0.3 * Math.random()) const radius = m.fieldRange * (0.6 + 0.3 * Math.random())
b.iceIX(6 + 6 * Math.random(), angle, Vector.add(m.fieldPosition, { b.iceIX(6 + 6 * Math.random(), angle, Vector.add(m.fieldPosition, {
@@ -2853,16 +2831,18 @@ const m = {
}); //set velocity to cap, but keep the direction }); //set velocity to cap, but keep the direction
} }
// go invulnerable while field is active, but also drain energy
// if (true && m.energy > 2 * m.fieldRegen && m.immuneCycle < m.cycle + tech.cyclicImmunity) {
// m.immuneCycle = m.cycle + 1; //player is immune to damage for 60 cycles
// m.energy -= 2 * m.fieldRegen
// if (m.energy < m.fieldRegen) m.fieldCDcycle = m.cycle + 90;
// }
if (m.energy > m.fieldRegen) m.energy -= m.fieldRegen if (m.energy > m.fieldRegen) m.energy -= m.fieldRegen
m.grabPowerUp(); m.grabPowerUp();
m.lookForPickUp(); m.lookForPickUp();
m.fieldPosition = { m.fieldPosition = { x: m.pos.x, y: m.pos.y }
x: m.pos.x,
y: m.pos.y
}
m.fieldAngle = m.angle m.fieldAngle = m.angle
//draw field attached to player //draw field attached to player
if (m.holdingTarget) { if (m.holdingTarget) {
@@ -3215,61 +3195,6 @@ const m = {
} }
} }
}, },
// {
// name: "plasma torch",
// description: "use <strong class='color-f'>energy</strong> to emit short range <strong class='color-plasma'>plasma</strong><br><strong class='color-d'>damages</strong> and <strong>pushes</strong> mobs away",
// effect() {
// m.fieldMeterColor = "#f0f"
// m.eyeFillColor = m.fieldMeterColor
// m.hold = function() {
// b.isExtruderOn = false
// if (m.isHolding) {
// m.drawHold(m.holdingTarget);
// m.holding();
// m.throwBlock();
// } else if (input.field && m.fieldCDcycle < m.cycle) { //not hold but field button is pressed
// m.grabPowerUp();
// m.lookForPickUp();
// if (tech.isExtruder) {
// b.extruder();
// } else {
// b.plasma();
// }
// } else if (m.holdingTarget && m.fieldCDcycle < m.cycle) { //holding, but field button is released
// m.pickUp();
// } else {
// m.holdingTarget = null; //clears holding target (this is so you only pick up right after the field button is released and a hold target exists)
// }
// m.drawRegenEnergy("rgba(0, 0, 0, 0.2)")
// if (tech.isExtruder) {
// if (input.field) {
// b.wasExtruderOn = true
// } else {
// b.wasExtruderOn = false
// b.canExtruderFire = true
// }
// ctx.beginPath(); //draw all the wave bullets
// for (let i = 0, len = bullet.length; i < len; i++) {
// if (bullet[i].isWave) {
// if (bullet[i].isBranch) {
// ctx.moveTo(bullet[i].position.x, bullet[i].position.y)
// } else {
// ctx.lineTo(bullet[i].position.x, bullet[i].position.y)
// }
// }
// }
// if (b.wasExtruderOn && b.isExtruderOn) ctx.lineTo(m.pos.x + 15 * Math.cos(m.angle), m.pos.y + 15 * Math.sin(m.angle))
// ctx.lineWidth = 4;
// ctx.strokeStyle = "#f07"
// ctx.stroke();
// ctx.lineWidth = tech.extruderRange;
// ctx.strokeStyle = "rgba(255,0,110,0.05)"
// ctx.stroke();
// }
// }
// }
// },
{ {
name: "plasma torch", name: "plasma torch",
description: "use <strong class='color-f'>energy</strong> to emit short range <strong class='color-plasma'>plasma</strong><br><strong class='color-d'>damages</strong> and <strong>pushes</strong> mobs away<br>generate <strong>10</strong> <strong class='color-f'>energy</strong> per second", description: "use <strong class='color-f'>energy</strong> to emit short range <strong class='color-plasma'>plasma</strong><br><strong class='color-d'>damages</strong> and <strong>pushes</strong> mobs away<br>generate <strong>10</strong> <strong class='color-f'>energy</strong> per second",
@@ -3721,7 +3646,7 @@ const m = {
m.throwBlock(); m.throwBlock();
m.wakeCheck(); m.wakeCheck();
} else if (input.field && m.fieldCDcycle < m.cycle) { //not hold but field button is pressed } else if (input.field && m.fieldCDcycle < m.cycle) { //not hold but field button is pressed
const drain = 0.0014 / (1 + 0.5 * m.coupling) const drain = 0.0014 / (1 + 0.05 * m.coupling)
if (m.energy > drain) m.energy -= drain if (m.energy > drain) m.energy -= drain
m.grabPowerUp(); m.grabPowerUp();
if (this.rewindCount === 0) { if (this.rewindCount === 0) {
@@ -3810,7 +3735,7 @@ const m = {
m.holding(); m.holding();
m.throwBlock(); m.throwBlock();
} else if (input.field && m.fieldCDcycle < m.cycle) { } else if (input.field && m.fieldCDcycle < m.cycle) {
const drain = 0.0026 / (1 + 0.3 * m.coupling) const drain = 0.0026 / (1 + 0.03 * m.coupling)
if (m.energy > drain) m.energy -= drain if (m.energy > drain) m.energy -= drain
m.grabPowerUp(); m.grabPowerUp();
m.lookForPickUp(); //this drains energy 0.001 m.lookForPickUp(); //this drains energy 0.001
@@ -3870,6 +3795,33 @@ const m = {
m.isSneakAttack = true; m.isSneakAttack = true;
m.sneakAttackCycle = 0; m.sneakAttackCycle = 0;
m.enterCloakCycle = 0; m.enterCloakCycle = 0;
m.drawCloakedM = function () {
m.walk_cycle -= m.flipLegs * m.Vx;
m.draw();
// let history = m.history[(m.cycle - 1) % 600]
// m.pos.x = history.position.x
// m.pos.y = history.position.y + m.yPosDifference - history.yOff
// m.pos.x += 4
// ctx.fillStyle = m.fillColor;
// ctx.save();
// ctx.translate(m.pos.x, m.pos.y);
// m.calcLeg(Math.PI, -3);
// m.drawLeg("#ccc");
// m.calcLeg(0, 0);
// m.drawLeg("#ccc");
// ctx.rotate(m.angle);
// ctx.beginPath();
// ctx.arc(0, 0, 30, 0, 2 * Math.PI);
// ctx.fillStyle = "#fff"
// ctx.fill();
// ctx.arc(15, 0, 4, 0, 2 * Math.PI);
// ctx.strokeStyle = "#333";
// ctx.lineWidth = 2;
// ctx.stroke();
// ctx.restore()
}
m.drawCloak = function () { m.drawCloak = function () {
m.fieldPhase += 0.007 m.fieldPhase += 0.007
const wiggle = 0.15 * Math.sin(m.fieldPhase * 0.5) const wiggle = 0.15 * Math.sin(m.fieldPhase * 0.5)
@@ -3905,6 +3857,7 @@ const m = {
if (!m.isCloak && m.energy > drain + 0.03) { if (!m.isCloak && m.energy > drain + 0.03) {
m.energy -= drain m.energy -= drain
m.isCloak = true //enter cloak m.isCloak = true //enter cloak
m.fieldHarmReduction = 0.5;
m.enterCloakCycle = m.cycle m.enterCloakCycle = m.cycle
if (tech.isCloakHealLastHit && m.lastHit > 0) { if (tech.isCloakHealLastHit && m.lastHit > 0) {
const heal = Math.min(0.75 * m.lastHit, m.energy) const heal = Math.min(0.75 * m.lastHit, m.energy)
@@ -3930,6 +3883,8 @@ const m = {
} else if (m.isCloak) { //exit cloak } else if (m.isCloak) { //exit cloak
m.sneakAttackCycle = m.cycle m.sneakAttackCycle = m.cycle
m.isCloak = false m.isCloak = false
m.fieldHarmReduction = 1
if (tech.isIntangible) { if (tech.isIntangible) {
for (let i = 0; i < bullet.length; i++) { for (let i = 0; i < bullet.length; i++) {
if (bullet[i].botType && bullet[i].botType !== "orbit") bullet[i].collisionFilter.mask = cat.map | cat.body | cat.bullet | cat.mob | cat.mobBullet | cat.mobShield if (bullet[i].botType && bullet[i].botType !== "orbit") bullet[i].collisionFilter.mask = cat.map | cat.body | cat.bullet | cat.mob | cat.mobBullet | cat.mobShield
@@ -3963,6 +3918,9 @@ const m = {
m.fieldRange = m.fieldRange * 0.85 + 130 m.fieldRange = m.fieldRange * 0.85 + 130
m.fieldDrawRadius = m.fieldRange * 1.1 //* 0.88 //* Math.min(1, 0.3 + 0.5 * Math.min(1, energy * energy)); m.fieldDrawRadius = m.fieldRange * 1.1 //* 0.88 //* Math.min(1, 0.3 + 0.5 * Math.min(1, energy * energy));
m.drawCloak() m.drawCloak()
ctx.globalCompositeOperation = "lighter";
m.drawCloakedM()
ctx.globalCompositeOperation = "source-over";
} else if (m.fieldRange < 4000) { } else if (m.fieldRange < 4000) {
m.fieldRange += 90 m.fieldRange += 90
m.fieldDrawRadius = m.fieldRange //* Math.min(1, 0.3 + 0.5 * Math.min(1, energy * energy)); m.fieldDrawRadius = m.fieldRange //* Math.min(1, 0.3 + 0.5 * Math.min(1, energy * energy));
@@ -3985,153 +3943,14 @@ const m = {
} }
} }
this.drawRegenEnergyCloaking() this.drawRegenEnergyCloaking()
//show sneak attack status if (m.isSneakAttack && m.sneakAttackCycle + Math.min(120, 0.5 * (m.cycle - m.enterCloakCycle)) > m.cycle) { //show sneak attack status
// if (m.cycle > m.lastKillCycle + 240) { ctx.globalCompositeOperation = "multiply";
// if (m.sneakAttackCharge > 0) { m.drawCloakedM()
// if (m.sneakAttackCycle + Math.min(120, 0.7 * (m.cycle - m.enterCloakCycle)) > m.cycle) { ctx.globalCompositeOperation = "source-over";
// ctx.strokeStyle = "rgba(0,0,0,0.5)" //m.fieldMeterColor; //"rgba(255,255,0,0.2)" //ctx.strokeStyle = `rgba(0,0,255,${0.5+0.5*Math.random()})` }
// ctx.beginPath();
// ctx.arc(simulation.mouseInGame.x, simulation.mouseInGame.y, 16, 0, 2 * Math.PI);
// ctx.fillStyle = "rgba(0,0,0,0.2)"
// ctx.fill();
// }
} }
} }
}, },
// {
// name: "phase decoherence field",
// description: "use <strong class='color-f'>energy</strong> to become <strong>intangible</strong><br><strong>firing</strong> and touching <strong>shields</strong> <strong>drains</strong> <strong class='color-f'>energy</strong><br>unable to <strong>see</strong> and be <strong>seen</strong> by mobs",
// effect: () => {
// m.fieldFire = true;
// m.fieldMeterColor = "#fff";
// m.fieldPhase = 0;
// m.hold = function () {
// function drawField(radius) {
// radius *= Math.min(4, 0.9 + 2.2 * m.energy * m.energy);
// const rotate = m.cycle * 0.005;
// m.fieldPhase += 0.5 - 0.5 * Math.sqrt(Math.max(0.01, Math.min(m.energy, 1)));
// const off1 = 1 + 0.06 * Math.sin(m.fieldPhase);
// const off2 = 1 - 0.06 * Math.sin(m.fieldPhase);
// ctx.beginPath();
// ctx.ellipse(m.pos.x, m.pos.y, radius * off1, radius * off2, rotate, 0, 2 * Math.PI);
// if (m.fireCDcycle > m.cycle && (input.field)) {
// ctx.lineWidth = 5;
// ctx.strokeStyle = `rgba(0, 204, 255,1)`
// ctx.stroke()
// }
// ctx.fillStyle = "#fff" //`rgba(0,0,0,${0.5+0.5*m.energy})`;
// ctx.globalCompositeOperation = "destination-in"; //in or atop
// ctx.fill();
// ctx.globalCompositeOperation = "source-over";
// ctx.clip();
// }
// m.isCloak = false //isCloak disables most uses of foundPlayer()
// player.collisionFilter.mask = cat.body | cat.map | cat.mob | cat.mobBullet | cat.mobShield //normal collisions
// if (m.isHolding) {
// if (this.fieldRange < 2000) {
// this.fieldRange += 100
// drawField(this.fieldRange)
// }
// m.drawHold(m.holdingTarget);
// m.holding();
// m.throwBlock();
// } else if (input.field) {
// m.grabPowerUp();
// m.lookForPickUp();
// if (m.fieldCDcycle < m.cycle) {
// // simulation.draw.bodyFill = "transparent"
// // simulation.draw.bodyStroke = "transparent"
// const DRAIN = 0.00013 + (m.fireCDcycle > m.cycle ? 0.005 : 0)
// if (m.energy > DRAIN) {
// m.energy -= DRAIN;
// // if (m.energy < 0.001) {
// // m.fieldCDcycle = m.cycle + 120;
// // m.energy = 0;
// // m.holdingTarget = null; //clears holding target (this is so you only pick up right after the field button is released and a hold target exists)
// // }
// this.fieldRange = this.fieldRange * 0.8 + 0.2 * 160
// drawField(this.fieldRange)
// m.isCloak = true //isCloak disables most uses of foundPlayer()
// player.collisionFilter.mask = cat.map
// let inPlayer = Matter.Query.region(mob, player.bounds)
// if (inPlayer.length > 0) {
// for (let i = 0; i < inPlayer.length; i++) {
// if (inPlayer[i].shield) {
// m.energy -= 0.005; //shields drain player energy
// //draw outline of shield
// ctx.fillStyle = `rgba(140,217,255,0.5)`
// ctx.fill()
// } else if (tech.superposition && inPlayer[i].isDropPowerUp) {
// // inPlayer[i].damage(0.4 * m.dmgScale); //damage mobs inside the player
// // m.energy += 0.005;
// mobs.statusStun(inPlayer[i], 300)
// //draw outline of mob in a few random locations to show blurriness
// const vertices = inPlayer[i].vertices;
// const off = 30
// for (let k = 0; k < 3; k++) {
// const xOff = off * (Math.random() - 0.5)
// const yOff = off * (Math.random() - 0.5)
// ctx.beginPath();
// ctx.moveTo(xOff + vertices[0].x, yOff + vertices[0].y);
// for (let j = 1, len = vertices.length; j < len; ++j) {
// ctx.lineTo(xOff + vertices[j].x, yOff + vertices[j].y);
// }
// ctx.lineTo(xOff + vertices[0].x, yOff + vertices[0].y);
// ctx.fillStyle = "rgba(0,0,0,0.1)"
// ctx.fill()
// }
// break;
// }
// }
// }
// } else {
// m.fieldCDcycle = m.cycle + 120;
// m.energy = 0;
// m.holdingTarget = null; //clears holding target (this is so you only pick up right after the field button is released and a hold target exists)
// drawField(this.fieldRange)
// }
// }
// } else if (m.holdingTarget && m.fieldCDcycle < m.cycle) { //holding, but field button is released
// m.pickUp();
// if (this.fieldRange < 2000) {
// this.fieldRange += 100
// drawField(this.fieldRange)
// }
// } else {
// // this.fieldRange = 3000
// if (this.fieldRange < 2000 && m.holdingTarget === null) {
// this.fieldRange += 100
// drawField(this.fieldRange)
// }
// m.holdingTarget = null; //clears holding target (this is so you only pick up right after the field button is released and a hold target exists)
// }
// if (m.energy < m.maxEnergy) {
// m.energy += m.fieldRegen;
// const xOff = m.pos.x - m.radius * m.maxEnergy
// const yOff = m.pos.y - 50
// ctx.fillStyle = "rgba(0, 0, 0, 0.3)";
// ctx.fillRect(xOff, yOff, 60 * m.maxEnergy, 10);
// ctx.fillStyle = m.fieldMeterColor;
// ctx.fillRect(xOff, yOff, 60 * m.energy, 10);
// ctx.beginPath()
// ctx.rect(xOff, yOff, 60 * m.maxEnergy, 10);
// ctx.strokeStyle = "rgb(0, 0, 0)";
// ctx.lineWidth = 1;
// ctx.stroke();
// }
// if (m.energy < 0) m.energy = 0
// }
// }
// },
{ {
name: "pilot wave", name: "pilot wave",
//<br><strong class='color-block'>blocks</strong> can't <strong>collide</strong> with <strong>intangible</strong> mobs //<br><strong class='color-block'>blocks</strong> can't <strong>collide</strong> with <strong>intangible</strong> mobs
@@ -4450,7 +4269,7 @@ const m = {
Matter.Composite.remove(engine.world, body[i]); Matter.Composite.remove(engine.world, body[i]);
body.splice(i, 1); body.splice(i, 1);
m.fieldRange *= 0.8 m.fieldRange *= 0.8
if ((m.fieldMode === 0 || m.fieldMode === 9) && m.immuneCycle < m.cycle) m.energy += 0.2 * m.coupling if ((m.fieldMode === 0 || m.fieldMode === 9) && m.immuneCycle < m.cycle) m.energy += 0.02 * m.coupling
if (tech.isWormholeWorms) { //pandimensional spermia if (tech.isWormholeWorms) { //pandimensional spermia
b.worm(Vector.add(m.hole.pos2, Vector.rotate({ x: m.fieldRange * 0.4, y: 0 }, 2 * Math.PI * Math.random()))) b.worm(Vector.add(m.hole.pos2, Vector.rotate({ x: m.fieldRange * 0.4, y: 0 }, 2 * Math.PI * Math.random())))
Matter.Body.setVelocity(bullet[bullet.length - 1], Vector.mult(Vector.rotate(m.hole.unit, Math.PI / 2), -10)); Matter.Body.setVelocity(bullet[bullet.length - 1], Vector.mult(Vector.rotate(m.hole.unit, Math.PI / 2), -10));
@@ -4474,8 +4293,8 @@ const m = {
m.fieldRange *= 0.8 m.fieldRange *= 0.8
// if (tech.isWormholeEnergy && m.energy < m.maxEnergy * 2) m.energy = m.maxEnergy * 2 // if (tech.isWormholeEnergy && m.energy < m.maxEnergy * 2) m.energy = m.maxEnergy * 2
// if (tech.isWormholeEnergy && m.immuneCycle < m.cycle) m.energy += 0.5 // if (tech.isWormholeEnergy && m.immuneCycle < m.cycle) m.energy += 0.5
if ((m.fieldMode === 0 || m.fieldMode === 9) && m.immuneCycle < m.cycle) m.energy += 0.2 * m.coupling if ((m.fieldMode === 0 || m.fieldMode === 9) && m.immuneCycle < m.cycle) m.energy += 0.02 * m.coupling
if (m.fieldMode === 0 || m.fieldMode === 9) m.energy += 0.2 * m.coupling if (m.fieldMode === 0 || m.fieldMode === 9) m.energy += 0.02 * m.coupling
if (tech.isWormholeWorms) { //pandimensional spermia if (tech.isWormholeWorms) { //pandimensional spermia
b.worm(Vector.add(m.hole.pos1, Vector.rotate({ b.worm(Vector.add(m.hole.pos1, Vector.rotate({
x: m.fieldRange * 0.4, x: m.fieldRange * 0.4,
@@ -4528,7 +4347,7 @@ const m = {
if (input.field) { if (input.field) {
if (tech.isWormHolePause) { if (tech.isWormHolePause) {
const drain = m.fieldRegen + 0.0002 const drain = m.fieldRegen + 0.00004
if (m.energy > drain) { if (m.energy > drain) {
m.energy -= drain m.energy -= drain
if (m.immuneCycle < m.cycle + 1) m.immuneCycle = m.cycle + 1; //player is immune to damage for 1 cycle if (m.immuneCycle < m.cycle + 1) m.immuneCycle = m.cycle + 1; //player is immune to damage for 1 cycle

View File

@@ -351,7 +351,7 @@ const powerUps = {
simulation.paused = true; simulation.paused = true;
document.getElementById("choose-grid").style.opacity = "1" document.getElementById("choose-grid").style.opacity = "1"
} }
document.getElementById("choose-grid").style.transitionDuration = "0.25s"; //how long is the fade in on document.getElementById("choose-grid").style.transitionDuration = "0.5s"; //how long is the fade in on
document.getElementById("choose-grid").style.visibility = "visible" document.getElementById("choose-grid").style.visibility = "visible"
requestAnimationFrame(() => { requestAnimationFrame(() => {
@@ -429,7 +429,7 @@ const powerUps = {
return 13; return 13;
}, },
effect() { effect() {
m.couplingChange(0.1) m.couplingChange(1)
}, },
// spawnDelay(num) { // spawnDelay(num) {
// let count = num // let count = num
@@ -1069,7 +1069,6 @@ const powerUps = {
for (let j = 0, len = tech.tech[i].frequency; j < len; j++) options.push(i); for (let j = 0, len = tech.tech[i].frequency; j < len; j++) options.push(i);
} }
} }
function removeOption(index) { function removeOption(index) {
for (let i = options.length - 1; i > -1; i--) { for (let i = options.length - 1; i > -1; i--) {
if (index === options[i]) { if (index === options[i]) {
@@ -1321,24 +1320,10 @@ const powerUps = {
tech.isFlipFlopOn = false tech.isFlipFlopOn = false
if (document.getElementById("tech-switch")) document.getElementById("tech-switch").innerHTML = ` = <strong>OFF</strong>` if (document.getElementById("tech-switch")) document.getElementById("tech-switch").innerHTML = ` = <strong>OFF</strong>`
m.eyeFillColor = 'transparent' m.eyeFillColor = 'transparent'
if (tech.isFlipFlopCoupling) {
m.couplingChange(-5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
spawn.WIMP()
mob[mob.length - 1].isDecoupling = true //so you can find it to remove
}
} else { } else {
tech.isFlipFlopOn = true //immune to damage this hit, lose immunity for next hit tech.isFlipFlopOn = true //immune to damage this hit, lose immunity for next hit
if (document.getElementById("tech-switch")) document.getElementById("tech-switch").innerHTML = ` = <strong>ON</strong>` if (document.getElementById("tech-switch")) document.getElementById("tech-switch").innerHTML = ` = <strong>ON</strong>`
m.eyeFillColor = m.fieldMeterColor //'#0cf' m.eyeFillColor = m.fieldMeterColor //'#0cf'
if (tech.isFlipFlopCoupling) {
m.couplingChange(5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
} }
if (tech.isRelayEnergy) m.setMaxEnergy(); if (tech.isRelayEnergy) m.setMaxEnergy();
} }

View File

@@ -20,7 +20,6 @@ const simulation = {
mobs.draw(); mobs.draw();
simulation.draw.cons(); simulation.draw.cons();
simulation.draw.body(); simulation.draw.body();
simulation.checks();
if (!m.isBodiesAsleep) mobs.loop(); if (!m.isBodiesAsleep) mobs.loop();
mobs.healthBar(); mobs.healthBar();
m.draw(); m.draw();
@@ -51,7 +50,6 @@ const simulation = {
} }
m.move(); m.move();
m.look(); m.look();
simulation.checks();
simulation.camera(); simulation.camera();
level.custom(); level.custom();
m.draw(); m.draw();
@@ -90,7 +88,6 @@ const simulation = {
} }
m.move(); m.move();
level.custom(); level.custom();
simulation.checks();
mobs.loop(); mobs.loop();
m.walk_cycle += m.flipLegs * m.Vx; m.walk_cycle += m.flipLegs * m.Vx;
m.hold(); m.hold();
@@ -111,7 +108,6 @@ const simulation = {
Engine.update(engine, simulation.delta); Engine.update(engine, simulation.delta);
// level.custom(); // level.custom();
// level.customTopLayer(); // level.customTopLayer();
simulation.checks();
if (!m.isBodiesAsleep) mobs.loop(); if (!m.isBodiesAsleep) mobs.loop();
if (m.fieldMode !== 7) m.hold(); if (m.fieldMode !== 7) m.hold();
b.bulletRemove(); b.bulletRemove();
@@ -153,7 +149,6 @@ const simulation = {
// simulation.draw.cons(); // simulation.draw.cons();
// simulation.draw.body(); // simulation.draw.body();
// if (!m.isBodiesAsleep) { // if (!m.isBodiesAsleep) {
// simulation.checks();
// // mobs.loop(); // // mobs.loop();
// } // }
// mobs.healthBar(); // mobs.healthBar();
@@ -464,7 +459,7 @@ const simulation = {
// SVGleftMouse: '<svg viewBox="750 0 200 765" class="mouse-icon" width="40px" height = "60px" stroke-linecap="round" stroke-linejoin="round" stroke-width="25px" stroke="#000" fill="none"> <path fill="#fff" stroke="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M832.41,106.64 V323.55 H651.57 V256.64 c0-82.5,67.5-150,150-150 Z" fill="#149" stroke="none" /> <path fill="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M657 317 h 340 h-170 v-207" /> <ellipse fill="#fff" cx="827.57" cy="218.64" rx="29" ry="68" /> </svg>', // SVGleftMouse: '<svg viewBox="750 0 200 765" class="mouse-icon" width="40px" height = "60px" stroke-linecap="round" stroke-linejoin="round" stroke-width="25px" stroke="#000" fill="none"> <path fill="#fff" stroke="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M832.41,106.64 V323.55 H651.57 V256.64 c0-82.5,67.5-150,150-150 Z" fill="#149" stroke="none" /> <path fill="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M657 317 h 340 h-170 v-207" /> <ellipse fill="#fff" cx="827.57" cy="218.64" rx="29" ry="68" /> </svg>',
// SVGrightMouse: '<svg viewBox="750 0 200 765" class="mouse-icon" width="40px" height = "60px" stroke-linecap="round" stroke-linejoin="round" stroke-width="25px" stroke="#000" fill="none"> <path fill="#fff" stroke="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M827,112 h30 a140,140,0,0,1,140,140 v68 h-167 z" fill="#0cf" stroke="none" /> <path fill="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M657 317 h 340 h-170 v-207" /> <ellipse fill="#fff" cx="827.57" cy="218.64" rx="29" ry="68" /> </svg>', // SVGrightMouse: '<svg viewBox="750 0 200 765" class="mouse-icon" width="40px" height = "60px" stroke-linecap="round" stroke-linejoin="round" stroke-width="25px" stroke="#000" fill="none"> <path fill="#fff" stroke="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M827,112 h30 a140,140,0,0,1,140,140 v68 h-167 z" fill="#0cf" stroke="none" /> <path fill="none" d="M827,112 h30 a140,140,0,0,1,140,140 v268 a140,140,0,0,1-140,140 h-60 a140,140,0,0,1-140-140v-268 a140,140,0,0,1,140-140h60" /> <path d="M657 317 h 340 h-170 v-207" /> <ellipse fill="#fff" cx="827.57" cy="218.64" rx="29" ry="68" /> </svg>',
makeTextLog(text, time = 240) { makeTextLog(text, time = 240) {
if (simulation.isTextLogOpen && !build.isExperimentSelection) { if (!localSettings.isHideHUD && simulation.isTextLogOpen && !build.isExperimentSelection) {
if (simulation.lastLogTime > m.cycle) { //if there is an older message if (simulation.lastLogTime > m.cycle) { //if there is an older message
document.getElementById("text-log").innerHTML = document.getElementById("text-log").innerHTML + '<br>' + text; document.getElementById("text-log").innerHTML = document.getElementById("text-log").innerHTML + '<br>' + text;
simulation.lastLogTime = m.cycle + time; simulation.lastLogTime = m.cycle + time;
@@ -735,12 +730,18 @@ const simulation = {
document.getElementById("dmg").style.display = "inline"; document.getElementById("dmg").style.display = "inline";
document.getElementById("health").style.display = "inline" document.getElementById("health").style.display = "inline"
document.getElementById("health-bg").style.display = "inline"; document.getElementById("health-bg").style.display = "inline";
document.getElementById("defense-bar").style.display = "inline" if (!localSettings.isHideHUD) {
document.getElementById("damage-bar").style.display = "inline" document.getElementById("tech").style.display = "inline"
document.getElementById("defense-bar").style.display = "inline"
document.getElementById("tech").style.display = "inline" document.getElementById("damage-bar").style.display = "inline"
} else {
document.getElementById("tech").style.display = "none"
document.getElementById("defense-bar").style.display = "none"
document.getElementById("damage-bar").style.display = "none"
}
document.getElementById("guns").style.display = "inline" document.getElementById("guns").style.display = "inline"
document.getElementById("field").style.display = "inline" document.getElementById("field").style.display = "inline"
// document.body.style.overflow = "hidden" // document.body.style.overflow = "hidden"
document.getElementById("pause-grid-left").style.display = "none" document.getElementById("pause-grid-left").style.display = "none"
document.getElementById("pause-grid-right").style.display = "none" document.getElementById("pause-grid-right").style.display = "none"
@@ -878,6 +879,138 @@ const simulation = {
build.isExperimentSelection = false; build.isExperimentSelection = false;
build.isExperimentRun = false; build.isExperimentRun = false;
//setup checks
if (!localSettings.isHideHUD) {
simulation.ephemera.push({
name: "dmgDefBars", count: 0, do() {
if (!(m.cycle % 15)) { //4 times a second
const defense = m.defense() //update defense bar
if (m.lastCalculatedDefense !== defense) {
document.getElementById("defense-bar").style.width = Math.floor(300 * m.maxHealth * (1 - defense)) + "px";
m.lastCalculatedDefense = defense
}
const damage = tech.damageFromTech() //update damage bar
if (m.lastCalculatedDamage !== damage) {
document.getElementById("damage-bar").style.height = Math.floor((Math.atan(0.25 * damage - 0.25) + 0.25) * 0.53 * canvas.height) + "px";
m.lastCalculatedDamage = damage
}
}
},
})
}
simulation.ephemera.push({
name: "uniqueName", count: 0, do() {
if (!(m.cycle % 60)) { //once a second
//energy overfill
if (m.energy > m.maxEnergy) {
m.energy = m.maxEnergy + (m.energy - m.maxEnergy) * tech.overfillDrain //every second energy above max energy loses 25%
if (m.energy > 1000000) m.energy = 1000000
}
if (tech.isFlipFlopEnergy && m.immuneCycle < m.cycle) {
if (tech.isFlipFlopOn) {
if (m.immuneCycle < m.cycle) m.energy += 0.2;
} else {
m.energy -= 0.01;
if (m.energy < 0) m.energy = 0
}
}
if (tech.relayIce && tech.isFlipFlopOn) {
for (let j = 0; j < tech.relayIce; j++) {
for (let i = 0, len = 3 + Math.ceil(9 * Math.random()); i < len; i++) b.iceIX(2)
}
}
if (m.pos.y > simulation.fallHeight) { // if 4000px deep
Matter.Body.setVelocity(player, {
x: 0,
y: 0
});
Matter.Body.setPosition(player, {
x: level.enter.x + 50,
y: level.enter.y - 20
});
// move bots
for (let i = 0; i < bullet.length; i++) {
if (bullet[i].botType) {
Matter.Body.setPosition(bullet[i], Vector.add(player.position, {
x: 250 * (Math.random() - 0.5),
y: 250 * (Math.random() - 0.5)
}));
Matter.Body.setVelocity(bullet[i], {
x: 0,
y: 0
});
}
}
m.damage(0.1 * simulation.difficultyMode);
m.energy -= 0.1 * simulation.difficultyMode
}
if (isNaN(player.position.x)) m.death();
if (m.lastKillCycle + 300 > m.cycle) { //effects active for 5 seconds after killing a mob
if (tech.isEnergyRecovery && m.immuneCycle < m.cycle) {
m.energy += m.maxEnergy * 0.05
simulation.drawList.push({ //add dmg to draw queue
x: m.pos.x,
y: m.pos.y - 45,
radius: Math.sqrt(m.maxEnergy * 0.05) * 60,
color: "rgba(0, 204, 255,0.4)", //#0cf
time: 4
});
}
if (tech.isHealthRecovery) {
const heal = 0.005 * m.maxHealth
m.addHealth(heal)
simulation.drawList.push({ //add dmg to draw queue
x: m.pos.x,
y: m.pos.y,
radius: Math.sqrt(heal) * 150,
color: "rgba(0,255,200,0.5)",
time: 4
});
}
}
if (!(m.cycle % 420)) { //once every 7 seconds
if (tech.isZeno) {
if (tech.isEnergyHealth) {
m.energy *= 0.95
} else {
m.health *= 0.95 //remove 5%
m.displayHealth();
}
}
if (tech.cyclicImmunity && m.immuneCycle < m.cycle + tech.cyclicImmunity) m.immuneCycle = m.cycle + tech.cyclicImmunity; //player is immune to damage for 60 cycles
fallCheck = function (who, save = false) {
let i = who.length;
while (i--) {
if (who[i].position.y > simulation.fallHeight) {
if (save) {
Matter.Body.setVelocity(who[i], {
x: 0,
y: 0
});
Matter.Body.setPosition(who[i], {
x: level.exit.x + 30 * (Math.random() - 0.5),
y: level.exit.y + 30 * (Math.random() - 0.5)
});
} else {
Matter.Composite.remove(engine.world, who[i]);
who.splice(i, 1);
}
}
}
};
fallCheck(mob);
fallCheck(body);
fallCheck(powerUp, true);
}
}
},
})
//setup FPS cap //setup FPS cap
simulation.fpsInterval = 1000 / simulation.fpsCap; simulation.fpsInterval = 1000 / simulation.fpsCap;
simulation.then = Date.now(); simulation.then = Date.now();
@@ -1172,127 +1305,6 @@ const simulation = {
// } // }
// } // }
// }, // },
checks() {
if (!(m.cycle % 15)) { //4 times a second
const defense = m.defense() //update defense bar
if (m.lastCalculatedDefense !== defense) {
document.getElementById("defense-bar").style.width = Math.floor(300 * m.maxHealth * (1 - defense)) + "px";
m.lastCalculatedDefense = defense
}
const damage = tech.damageFromTech() //update damage bar
if (m.lastCalculatedDamage !== damage) {
document.getElementById("damage-bar").style.height = Math.floor((Math.atan(0.25 * damage - 0.25) + 0.25) * 0.53 * canvas.height) + "px";
m.lastCalculatedDamage = damage
}
}
if (!(m.cycle % 60)) { //once a second
//energy overfill
if (m.energy > m.maxEnergy) {
m.energy = m.maxEnergy + (m.energy - m.maxEnergy) * tech.overfillDrain //every second energy above max energy loses 25%
if (m.energy > 1000000) m.energy = 1000000
}
if (tech.isFlipFlopEnergy && m.immuneCycle < m.cycle) {
if (tech.isFlipFlopOn) {
if (m.immuneCycle < m.cycle) m.energy += 0.2;
} else {
m.energy -= 0.01;
if (m.energy < 0) m.energy = 0
}
}
if (tech.relayIce && tech.isFlipFlopOn) {
for (let j = 0; j < tech.relayIce; j++) {
for (let i = 0, len = 3 + Math.ceil(9 * Math.random()); i < len; i++) b.iceIX(2)
}
}
if (m.pos.y > simulation.fallHeight) { // if 4000px deep
Matter.Body.setVelocity(player, {
x: 0,
y: 0
});
Matter.Body.setPosition(player, {
x: level.enter.x + 50,
y: level.enter.y - 20
});
// move bots
for (let i = 0; i < bullet.length; i++) {
if (bullet[i].botType) {
Matter.Body.setPosition(bullet[i], Vector.add(player.position, {
x: 250 * (Math.random() - 0.5),
y: 250 * (Math.random() - 0.5)
}));
Matter.Body.setVelocity(bullet[i], {
x: 0,
y: 0
});
}
}
m.damage(0.1 * simulation.difficultyMode);
m.energy -= 0.1 * simulation.difficultyMode
}
if (isNaN(player.position.x)) m.death();
if (m.lastKillCycle + 300 > m.cycle) { //effects active for 5 seconds after killing a mob
if (tech.isEnergyRecovery && m.immuneCycle < m.cycle) {
m.energy += m.maxEnergy * 0.05
simulation.drawList.push({ //add dmg to draw queue
x: m.pos.x,
y: m.pos.y - 45,
radius: Math.sqrt(m.maxEnergy * 0.05) * 60,
color: "rgba(0, 204, 255,0.4)", //#0cf
time: 4
});
}
if (tech.isHealthRecovery) {
const heal = 0.005 * m.maxHealth
m.addHealth(heal)
simulation.drawList.push({ //add dmg to draw queue
x: m.pos.x,
y: m.pos.y,
radius: Math.sqrt(heal) * 150,
color: "rgba(0,255,200,0.5)",
time: 4
});
}
}
if (!(m.cycle % 420)) { //once every 7 seconds
if (tech.isZeno) {
if (tech.isEnergyHealth) {
m.energy *= 0.95
} else {
m.health *= 0.95 //remove 5%
m.displayHealth();
}
}
if (tech.cyclicImmunity && m.immuneCycle < m.cycle + tech.cyclicImmunity) m.immuneCycle = m.cycle + tech.cyclicImmunity; //player is immune to damage for 60 cycles
fallCheck = function (who, save = false) {
let i = who.length;
while (i--) {
if (who[i].position.y > simulation.fallHeight) {
if (save) {
Matter.Body.setVelocity(who[i], {
x: 0,
y: 0
});
Matter.Body.setPosition(who[i], {
x: level.exit.x + 30 * (Math.random() - 0.5),
y: level.exit.y + 30 * (Math.random() - 0.5)
});
} else {
Matter.Composite.remove(engine.world, who[i]);
who.splice(i, 1);
}
}
}
};
fallCheck(mob);
fallCheck(body);
fallCheck(powerUp, true);
}
}
},
testingOutput() { testingOutput() {
ctx.fillStyle = "#000"; ctx.fillStyle = "#000";
ctx.textAlign = "center"; ctx.textAlign = "center";

View File

@@ -220,20 +220,21 @@ const tech = {
damage: 1, //used for tech changes to player damage that don't have complex conditions damage: 1, //used for tech changes to player damage that don't have complex conditions
damageFromTech() { damageFromTech() {
let dmg = tech.damage //m.fieldDamage let dmg = tech.damage //m.fieldDamage
if (tech.isDivisor) { // if (tech.isDivisor) {
for (let i = 0; i < b.inventory.length; i++) { // for (let i = 0; i < b.inventory.length; i++) {
if (b.guns[b.inventory[i]].ammo % 3 === 0) { // if (b.guns[b.inventory[i]].ammo % 3 === 0) {
dmg *= 1.44 // dmg *= 1.44
break // break
} // }
} // }
} // }
if (tech.isDivisor && b.guns[b.activeGun].ammo % 3 === 0) dmg *= 1.83
if (tech.isNoGroundDamage) dmg *= m.onGround ? 0.78 : 1.88 if (tech.isNoGroundDamage) dmg *= m.onGround ? 0.78 : 1.88
if (tech.isDilate) dmg *= 1.5 + 0.6 * Math.sin(m.cycle * 0.0075) if (tech.isDilate) dmg *= 1.5 + 0.6 * Math.sin(m.cycle * 0.0075)
if (tech.isGunChoice && tech.buffedGun === b.inventoryGun) dmg *= 1 + 0.31 * b.inventory.length if (tech.isGunChoice && tech.buffedGun === b.inventoryGun) dmg *= 1 + 0.31 * b.inventory.length
if (powerUps.boost.endCycle > m.cycle) dmg *= 1 + powerUps.boost.damage if (powerUps.boost.endCycle > m.cycle) dmg *= 1 + powerUps.boost.damage
if (m.coupling && (m.fieldMode === 0 || m.fieldMode === 5)) dmg *= 1 + 0.15 * m.coupling if (m.coupling && (m.fieldMode === 0 || m.fieldMode === 5)) dmg *= 1 + 0.015 * m.coupling
if (m.isSneakAttack && m.sneakAttackCycle + Math.min(120, 0.5 * (m.cycle - m.enterCloakCycle)) > m.cycle) dmg *= 4.33 * (1 + 0.33 * m.coupling) if (m.isSneakAttack && m.sneakAttackCycle + Math.min(120, 0.5 * (m.cycle - m.enterCloakCycle)) > m.cycle) dmg *= 4.33 * (1 + 0.033 * m.coupling)
if (tech.deathSkipTime) dmg *= 1 + 0.6 * tech.deathSkipTime if (tech.deathSkipTime) dmg *= 1 + 0.6 * tech.deathSkipTime
if (tech.isTechDebt) dmg *= tech.totalCount > 2 ? Math.pow(0.85, tech.totalCount - 20) : 4 - 0.15 * tech.totalCount // if (tech.isTechDebt) dmg *= Math.min(Math.pow(0.85, tech.totalCount - 20), 4 - 0.15 * tech.totalCount) if (tech.isTechDebt) dmg *= tech.totalCount > 2 ? Math.pow(0.85, tech.totalCount - 20) : 4 - 0.15 * tech.totalCount // if (tech.isTechDebt) dmg *= Math.min(Math.pow(0.85, tech.totalCount - 20), 4 - 0.15 * tech.totalCount)
if (tech.isFlipFlopDamage && tech.isFlipFlopOn) dmg *= 1.555 if (tech.isFlipFlopDamage && tech.isFlipFlopOn) dmg *= 1.555
@@ -258,7 +259,7 @@ const tech = {
return dmg return dmg
}, },
duplicationChance() { duplicationChance() {
return Math.min(1, Math.max(0, (tech.isPowerUpsVanish ? 0.12 : 0) + (tech.isStimulatedEmission ? 0.15 : 0) + tech.duplication + tech.duplicateChance + 0.05 * tech.isExtraGunField + m.duplicateChance + tech.fieldDuplicate + tech.cloakDuplication + (tech.isAnthropicTech && tech.isDeathAvoidedThisLevel ? 0.5 : 0) + tech.isQuantumEraserDuplication * (1 - 0.016 * (simulation.difficultyMode ** 2)))) // + (m.fieldMode === 0 || m.fieldMode === 9) * 0.03 * m.coupling) return Math.min(1, Math.max(0, (tech.isPowerUpsVanish ? 0.12 : 0) + (tech.isStimulatedEmission ? 0.15 : 0) + tech.duplication + tech.duplicateChance + 0.05 * tech.isExtraGunField + m.duplicateChance + tech.fieldDuplicate + tech.cloakDuplication + (tech.isAnthropicTech && tech.isDeathAvoidedThisLevel ? 0.5 : 0) + tech.isQuantumEraserDuplication * (1 - 0.016 * (simulation.difficultyMode ** 2))))
}, },
isScaleMobsWithDuplication: false, isScaleMobsWithDuplication: false,
maxDuplicationEvent() { maxDuplicationEvent() {
@@ -541,7 +542,7 @@ const tech = {
{ {
name: "ternary", //"divisor", name: "ternary", //"divisor",
descriptionFunction() { descriptionFunction() {
return `<strong>+44%</strong> <strong class='color-d'>damage</strong> while one of your <strong class='color-g'>guns</strong><br>has <strong class='color-ammo'>ammo</strong> divisible by <strong>3</strong>` return `<strong>+83%</strong> <strong class='color-d'>damage</strong> while your current <strong class='color-g'>gun</strong><br>has <strong class='color-ammo'>ammo</strong> divisible by <strong>3</strong>`
}, },
maxCount: 1, maxCount: 1,
count: 0, count: 0,
@@ -2146,12 +2147,6 @@ const tech = {
tech.isFlipFlop = true //do you have this tech? tech.isFlipFlop = true //do you have this tech?
if (!tech.isFlipFlopOn) { if (!tech.isFlipFlopOn) {
tech.isFlipFlopOn = true //what is the state of flip-Flop? tech.isFlipFlopOn = true //what is the state of flip-Flop?
if (tech.isFlipFlopCoupling) {
m.couplingChange(5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
} }
// if (!m.isShipMode) { // if (!m.isShipMode) {
// m.skin.flipFlop() // m.skin.flipFlop()
@@ -2161,12 +2156,6 @@ const tech = {
tech.isFlipFlop = false tech.isFlipFlop = false
if (tech.isFlipFlopOn) { if (tech.isFlipFlopOn) {
tech.isFlipFlopOn = false //what is the state of flip-Flop? tech.isFlipFlopOn = false //what is the state of flip-Flop?
if (tech.isFlipFlopCoupling) {
m.couplingChange(5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
} }
m.eyeFillColor = 'transparent' m.eyeFillColor = 'transparent'
// m.resetSkin(); // m.resetSkin();
@@ -2226,49 +2215,49 @@ const tech = {
tech.isFlipFlopEnergy = false; tech.isFlipFlopEnergy = false;
} }
}, },
{ // {
name: "decoupling", // name: "decoupling",
link: `<a target="_blank" href='https://en.wikipedia.org/wiki/Decoupling_(cosmology)' class="link">decoupling</a>`, // link: `<a target="_blank" href='https://en.wikipedia.org/wiki/Decoupling_(cosmology)' class="link">decoupling</a>`,
descriptionFunction() { // descriptionFunction() {
//<span style = 'font-size:80%;'>(${ m.couplingDescription(this.bonus)})</span> // //<span style = 'font-size:80%;'>(${ m.couplingDescription(this.bonus)})</span>
return `if <strong class='color-flop'>ON</strong> <strong>+5</strong> <strong class='color-coupling'>coupling</strong><br>if <strong class='color-flop'>OFF</strong> a dangerous particle slowly <strong>chases</strong> you` // return `if <strong class='color-flop'>ON</strong> <strong>+5</strong> <strong class='color-coupling'>coupling</strong><br>if <strong class='color-flop'>OFF</strong> a dangerous particle slowly <strong>chases</strong> you`
}, // },
maxCount: 1, // maxCount: 1,
count: 0, // count: 0,
frequency: 3, // frequency: 3,
frequencyDefault: 3, // frequencyDefault: 3,
bonus: 5, //coupling given // bonus: 5, //coupling given
allowed() { // allowed() {
return tech.isFlipFlop || tech.isRelay // return tech.isFlipFlop || tech.isRelay
}, // },
requires: "ON/OFF tech", // requires: "ON/OFF tech",
effect() { // effect() {
tech.isFlipFlopCoupling = true; // tech.isFlipFlopCoupling = true;
if (tech.isFlipFlopOn) { // if (tech.isFlipFlopOn) {
m.couplingChange(this.bonus) // m.couplingChange(this.bonus)
} else { // } else {
for (let i = 0; i < mob.length; i++) { // for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP // if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
} // }
spawn.WIMP() // spawn.WIMP()
mob[mob.length - 1].isDecoupling = true //so you can find it to remove // mob[mob.length - 1].isDecoupling = true //so you can find it to remove
} // }
}, // },
remove() { // remove() {
tech.isFlipFlopCoupling = false; // tech.isFlipFlopCoupling = false;
if (this.count) { // if (this.count) {
if (tech.isFlipFlop || tech.isRelay) { // if (tech.isFlipFlop || tech.isRelay) {
if (tech.isFlipFlopOn) { // if (tech.isFlipFlopOn) {
m.couplingChange(-this.bonus) // m.couplingChange(-this.bonus)
} else { // } else {
for (let i = 0; i < mob.length; i++) { // for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP // if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
} // }
} // }
} // }
} // }
} // }
}, // },
{ {
name: "relay switch", name: "relay switch",
description: `toggle <strong class="color-flop">ON</strong> and <strong class="color-flop">OFF</strong> after picking up a <strong>power up</strong><br>unlock advanced <strong class='color-m'>tech</strong> that runs if <strong class="color-flop">ON</strong>`, description: `toggle <strong class="color-flop">ON</strong> and <strong class="color-flop">OFF</strong> after picking up a <strong>power up</strong><br>unlock advanced <strong class='color-m'>tech</strong> that runs if <strong class="color-flop">ON</strong>`,
@@ -2299,12 +2288,6 @@ const tech = {
tech.isRelay = true //do you have this tech? tech.isRelay = true //do you have this tech?
if (!tech.isFlipFlopOn) { if (!tech.isFlipFlopOn) {
tech.isFlipFlopOn = true //what is the state of flip-Flop? tech.isFlipFlopOn = true //what is the state of flip-Flop?
if (tech.isFlipFlopCoupling) {
m.couplingChange(5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
} }
// if (!m.isShipMode) { // if (!m.isShipMode) {
// m.skin.flipFlop() // m.skin.flipFlop()
@@ -2314,12 +2297,6 @@ const tech = {
tech.isRelay = false tech.isRelay = false
if (tech.isFlipFlopOn) { if (tech.isFlipFlopOn) {
tech.isFlipFlopOn = false //what is the state of flip-Flop? tech.isFlipFlopOn = false //what is the state of flip-Flop?
if (tech.isFlipFlopCoupling) {
m.couplingChange(-5)
for (let i = 0; i < mob.length; i++) {
if (mob[i].isDecoupling) mob[i].alive = false //remove WIMP
}
}
} }
m.eyeFillColor = 'transparent' m.eyeFillColor = 'transparent'
// m.resetSkin(); // m.resetSkin();
@@ -3726,7 +3703,8 @@ const tech = {
{ {
name: "field coupling", name: "field coupling",
descriptionFunction() { descriptionFunction() {
return `spawn ${powerUps.orb.coupling(10)}<br>that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>` //<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"} // return `spawn ${powerUps.orb.coupling(10)}<br>that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>` //<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"}
return `spawn ${powerUps.orb.coupling(10)}<br><em>${m.couplingDescription(1)} per ${powerUps.orb.coupling(1)}</em>`
}, },
maxCount: 9, maxCount: 9,
count: 0, count: 0,
@@ -3740,9 +3718,7 @@ const tech = {
powerUps.spawnDelay("coupling", 10) powerUps.spawnDelay("coupling", 10)
}, },
remove() { remove() {
if (this.count) { if (this.count) m.couplingChange(-this.count * 10)
m.couplingChange(-this.count)
}
} }
}, },
{ {
@@ -3757,7 +3733,9 @@ const tech = {
} else { } else {
orbText = powerUps.orb.coupling(converted) orbText = powerUps.orb.coupling(converted)
} }
return `use all your ${powerUps.orb.research(1)} to spawn <strong>${orbText}</strong><br>that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>`//<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"} // return `use all your ${powerUps.orb.research(1)} to spawn <strong>${orbText}</strong><br>that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>`//<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"}
return `use all your ${powerUps.orb.research(1)} to spawn <strong>${orbText}</strong><br><em>${m.couplingDescription(1)} per ${powerUps.orb.coupling(1)}</em>`
}, },
maxCount: 1, maxCount: 1,
count: 0, count: 0,
@@ -3768,7 +3746,7 @@ const tech = {
}, },
requires: "", requires: "",
researchUsed: 0, researchUsed: 0,
couplingToResearch: 0.25, couplingToResearch: 3,
effect() { effect() {
// let count = 0 // let count = 0
// while (powerUps.research.count > 0 && powerUps.research.count !== Infinity) { // while (powerUps.research.count > 0 && powerUps.research.count !== Infinity) {
@@ -3802,7 +3780,8 @@ const tech = {
{ {
name: "virtual particles", name: "virtual particles",
descriptionFunction() { descriptionFunction() {
return `after mobs <strong>die</strong> they have a <strong>17%</strong> chance to<br>spawn ${powerUps.orb.coupling(1)} that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>` //<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"} return `<strong>17%</strong> chance after mobs <strong>die</strong> to spawn ${powerUps.orb.coupling(1)}<br><em>${m.couplingDescription(1)} per ${powerUps.orb.coupling(1)}</em>`
// return `<strong>17%</strong> chance after mobs <strong>die</strong> to spawn ${powerUps.orb.coupling(1)} that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>` //<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"}
}, },
maxCount: 1, maxCount: 1,
count: 0, count: 0,
@@ -3820,7 +3799,8 @@ const tech = {
{ {
name: "fine-structure constant", name: "fine-structure constant",
descriptionFunction() { descriptionFunction() {
return `spawn ${this.value} ${powerUps.orb.coupling(1)} that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong><br><strong>-0.5</strong> <strong class='color-coupling'>coupling</strong> after mob <strong>collisions</strong>`//<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"} // return `spawn ${this.value} ${powerUps.orb.coupling(1)} that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong><br><strong>-0.5</strong> <strong class='color-coupling'>coupling</strong> after mob <strong>collisions</strong>`//<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"}
return `spawn ${this.value} ${powerUps.orb.coupling(1)}, but <strong>lose</strong> ${powerUps.orb.coupling(5)} after mob <strong>collisions</strong><br><em>${m.couplingDescription(1)} per ${powerUps.orb.coupling(1)}</em>`
}, },
maxCount: 1, maxCount: 1,
count: 0, count: 0,
@@ -3835,16 +3815,15 @@ const tech = {
powerUps.spawnDelay("coupling", this.value) powerUps.spawnDelay("coupling", this.value)
}, },
remove() { remove() {
if (this.count) { if (this.count) m.couplingChange(-this.value)
m.couplingChange(-this.value)
}
tech.isCouplingNoHit = false tech.isCouplingNoHit = false
} }
}, },
{ {
name: "residual dipolar coupling", name: "residual dipolar coupling",
descriptionFunction() { descriptionFunction() {
return `clicking <strong class='color-cancel'>cancel</strong> for a <strong class='color-f'>field</strong>, <strong class='color-m'>tech</strong>, or <strong class='color-g'>gun</strong><br>spawns ${powerUps.orb.coupling(5)}that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>`//<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"} // return `clicking <strong class='color-cancel'>cancel</strong> for a <strong class='color-f'>field</strong>, <strong class='color-m'>tech</strong>, or <strong class='color-g'>gun</strong><br>spawns ${powerUps.orb.coupling(5)}that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>`//<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"}
return `clicking <strong class='color-cancel'>cancel</strong> spawns ${powerUps.orb.coupling(5)}<br><em>${m.couplingDescription(1)} per ${powerUps.orb.coupling(1)}</em>`
}, },
maxCount: 1, maxCount: 1,
count: 0, count: 0,
@@ -4092,7 +4071,7 @@ const tech = {
tech.damage *= this.damage tech.damage *= this.damage
}, },
remove() { remove() {
if (this.count > 0) { if (this.count > 0 && m.alive) {
tech.damage /= this.damage tech.damage /= this.damage
powerUps.spawnDelay("research", 15) powerUps.spawnDelay("research", 15)
this.frequency = 0 this.frequency = 0
@@ -7267,9 +7246,9 @@ const tech = {
frequency: 2, frequency: 2,
frequencyDefault: 2, frequencyDefault: 2,
allowed() { allowed() {
return (m.fieldMode === 4 && tech.deflectEnergy === 0) || (m.fieldMode === 1 && tech.harmonics === 2) || m.fieldMode === 0 return (m.fieldMode === 4 && tech.deflectEnergy === 0) || (m.fieldMode === 1 && tech.harmonics === 2)
}, },
requires: "molecular assembler, standing wave, field emitter, not electric generator", requires: "molecular assembler, standing wave, not electric generator",
effect() { effect() {
tech.isLaserField = true tech.isLaserField = true
}, },
@@ -7408,7 +7387,7 @@ const tech = {
{ {
name: "triple point", name: "triple point",
descriptionFunction() { descriptionFunction() {
return `<strong>+1.5</strong> second <strong class='color-s'>ice IX</strong> freeze effect<br>spawn ${powerUps.orb.coupling(10)} that each give <strong>+0.1</strong> <strong class='color-coupling'>coupling</strong>` //<br>${m.couplingDescription(1)} ${m.fieldMode === 0 ? "" : "per <strong class='color-coupling'>coupling</strong>"} return `<strong>+1.5</strong> second <strong class='color-s'>ice IX</strong> freeze and spawn ${powerUps.orb.coupling(10)}<br><em>${m.couplingDescription(1)} per ${powerUps.orb.coupling(1)}</em>`
}, },
isFieldTech: true, isFieldTech: true,
maxCount: 3, maxCount: 3,
@@ -7425,7 +7404,7 @@ const tech = {
}, },
remove() { remove() {
tech.iceIXFreezeTime = 150 tech.iceIXFreezeTime = 150
if (this.count) m.couplingChange(-this.count) if (this.count) m.couplingChange(-10 * this.count)
} }
}, },
{ {
@@ -8369,28 +8348,28 @@ const tech = {
}, },
{ {
name: "vacuum fluctuation", name: "vacuum fluctuation",
description: `use ${powerUps.orb.research(4)}to exploit your <strong class='color-f'>field</strong> for a<br><strong>+11%</strong> chance to <strong class='color-dup'>duplicate</strong> spawned <strong>power ups</strong>`, description: `use ${powerUps.orb.research(3)}to exploit your <strong class='color-f'>field</strong> for a<br><strong>+11%</strong> chance to <strong class='color-dup'>duplicate</strong> spawned <strong>power ups</strong>`,
isFieldTech: true, isFieldTech: true,
maxCount: 1, maxCount: 1,
count: 0, count: 0,
frequency: 3, frequency: 3,
frequencyDefault: 3, frequencyDefault: 3,
allowed() { allowed() {
return (m.fieldMode === 8 || m.fieldMode === 3 || m.fieldMode === 6 || m.fieldMode === 9) && (build.isExperimentSelection || powerUps.research.count > 3) return (m.fieldMode === 8 || m.fieldMode === 3 || m.fieldMode === 6 || m.fieldMode === 9) && (build.isExperimentSelection || powerUps.research.count > 2)
}, },
requires: "wormhole, time dilation, negative mass, pilot wave", requires: "wormhole, time dilation, negative mass, pilot wave",
effect() { effect() {
tech.fieldDuplicate = 0.11 tech.fieldDuplicate = 0.11
powerUps.setPowerUpMode(); //needed after adjusting duplication chance powerUps.setPowerUpMode(); //needed after adjusting duplication chance
if (!build.isExperimentSelection && !simulation.isTextLogOpen) simulation.circleFlare(0.11); if (!build.isExperimentSelection && !simulation.isTextLogOpen) simulation.circleFlare(0.11);
for (let i = 0; i < 4; i++) { for (let i = 0; i < 3; i++) {
if (powerUps.research.count > 0) powerUps.research.changeRerolls(-1) if (powerUps.research.count > 0) powerUps.research.changeRerolls(-1)
} }
}, },
remove() { remove() {
tech.fieldDuplicate = 0 tech.fieldDuplicate = 0
powerUps.setPowerUpMode(); //needed after adjusting duplication chance powerUps.setPowerUpMode(); //needed after adjusting duplication chance
if (this.count > 0) powerUps.research.changeRerolls(4) if (this.count > 0) powerUps.research.changeRerolls(3)
} }
}, },
// { // {
@@ -11523,7 +11502,6 @@ const tech = {
isCouplingPowerUps: null, isCouplingPowerUps: null,
isBoostPowerUps: null, isBoostPowerUps: null,
isBoostReplaceAmmo: null, isBoostReplaceAmmo: null,
isFlipFlopCoupling: null,
isInfiniteWaveAmmo: null, isInfiniteWaveAmmo: null,
isJunkDNA: null, isJunkDNA: null,
buffedGun: 0, buffedGun: 0,

View File

@@ -9,6 +9,7 @@ body {
margin: 0; margin: 0;
overflow: hidden; overflow: hidden;
cursor: auto; cursor: auto;
transition: background-color 0.2s ease-in-out;
} }
canvas { canvas {
@@ -183,6 +184,9 @@ summary {
scrollbar-width: none; scrollbar-width: none;
} }
.choose-grid-no-images { .choose-grid-no-images {
border-radius: 8px; border-radius: 8px;
border: 10px solid #444; border: 10px solid #444;
@@ -219,6 +223,9 @@ summary {
line-height: 160%; line-height: 160%;
background-color: var(--card-color); background-color: var(--card-color);
font-size: 0.75em; font-size: 0.75em;
/* transform-style: preserve-3d;
transition: transform 2s;
transform: rotateX(180deg); */
} }
.choose-grid-module:hover { .choose-grid-module:hover {

View File

@@ -1,27 +1,40 @@
******************************************************** NEXT PATCH ************************************************** ******************************************************** NEXT PATCH **************************************************
new community level - superNgonBros by DesBoot setting - minimal HUD
remove: defense bar, damage bar, tech, in game console
tech: induction brake - after using a heal slow nearby mobs for 15 seconds improved text clarity on coupling
tech: null hypothesis - +9 damage, spawn several research after removing removed tech decoupling
reworked: strange attractor - +7% damage, +10% duplication after removing
bremsstrahlung does 50% more damage added cloaking and sneak attack graphics
time crystals 200 -> 150% passive energy regen also, the 50% defense when cloaked is now clear from the defense bar
it also tells you how much energy regen you will get ternary 44->83% damage but requires current gun to have ammo/3 (was any gun)
aperture (-50 to +150) -> (-10 to +110) damage wormhole invariant: uses much less energy to pause time
diaphragm (-33 to +100) -> (+8 to +80) defense standing wave has less recoil when blocking
tungsten carbide 200 -> 222 health
CPT symmetry 30 -> 20 energy per second of rewind
quenching gives more max health, but also does more damage per over heal
final boss has 50% faster armor decay new images
so it takes even more damage the longer you fight it bug fixes
a few more images
some bug fixes
*********************************************************** TODO ***************************************************** *********************************************************** TODO *****************************************************
use ephemera to replace things
JUNK?
request animation stuff
simulation checks
damage and defense bars
disable and enable ephemera with settings
drones target anything that moves: speed > 1
including player, blocks?, mobs, power ups
maybe target the fastest mobs?
perfect diamagnatism - invulnerable while field is active?
also drain energy while field is active?
mobs attack mines
mines periodically set all mobs to have player location to be the mine
is this going to work with all mob vision types?
maybe use ⚆ in game text? maybe use ⚆ in game text?
increase font? increase font?
@@ -30,10 +43,6 @@ rework quantum eraser
test bremsstrahlung damage test bremsstrahlung damage
and make sure it actually does more damage with the dot tech and make sure it actually does more damage with the dot tech
use ephemera to replace things
JUNK?
request animation stuff
tech: choose next map by name after exiting current map tech: choose next map by name after exiting current map
use modified tech selection code? use modified tech selection code?
this might be too much work without much reward this might be too much work without much reward
@@ -1228,6 +1237,7 @@ if pause is pressed while selecting power ups, display pause menu on top of sele
time dilation - graphic of a hyperbolic equation Luminogram time dilation - graphic of a hyperbolic equation Luminogram
negative mass - Blacklight painting by Moebius negative mass - Blacklight painting by Moebius
plasma torch - by Dan Mumford plasma torch - by Dan Mumford
metamaterial cloaking - Scientific photography by Miki Asai, by Bruce Munro metamaterial cloaking - Scientific photography by Miki Asai, by Bruce Munro
molecular assembler - by Laurie Greasley 16-bit Isometric molecular assembler - by Laurie Greasley 16-bit Isometric
wormhole - by Tim White wormhole - by Tim White