rotary cannon

tech: rotary cannon - nail gun (and rivet gun) have increased fire rate, muzzle speed, recoil, and accuracy
experiment -parthenocarpy- spawn about 50% more mobs
This commit is contained in:
landgreen
2021-10-23 08:50:52 -07:00
parent 61b365ff6c
commit bac02c35f6
6 changed files with 244 additions and 92 deletions

BIN
.DS_Store vendored

Binary file not shown.

View File

@@ -4023,7 +4023,13 @@ const b = {
nextFireCycle: 0, //use to remember how longs its been since last fire, used to reset count nextFireCycle: 0, //use to remember how longs its been since last fire, used to reset count
startingHoldCycle: 0, startingHoldCycle: 0,
chooseFireMethod() { //set in simulation.startGame chooseFireMethod() { //set in simulation.startGame
if (tech.nailRecoil) {
if (tech.isRivets) { if (tech.isRivets) {
this.fire = this.fireRecoilRivets
} else {
this.fire = this.fireRecoilNails
}
} else if (tech.isRivets) {
this.fire = this.fireRivets this.fire = this.fireRivets
} else if (tech.isNeedles) { } else if (tech.isNeedles) {
this.fire = this.fireNeedles this.fire = this.fireNeedles
@@ -4036,8 +4042,37 @@ const b = {
} }
}, },
do() {}, do() {},
fire() { fire() {},
fireRecoilNails() {
if (this.nextFireCycle + 1 < m.cycle) this.startingHoldCycle = m.cycle //reset if not constantly firing
const CD = Math.max(11 - 0.08 * (m.cycle - this.startingHoldCycle), 1) //CD scales with cycles fire is held down
this.nextFireCycle = m.cycle + CD * b.fireCDscale //predict next fire cycle if the fire button is held down
m.fireCDcycle = m.cycle + Math.floor(CD * b.fireCDscale); // cool down
this.baseFire(m.angle + (Math.random() - 0.5) * (input.down ? 0.05 : 0.1) / CD, 43 + 8 * Math.random())
//very complex recoil system
if (m.onGround) {
if (input.down) {
const KNOCK = 0.01
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
Matter.Body.setVelocity(player, {
x: player.velocity.x * 0.5,
y: player.velocity.y * 0.5
});
} else {
const KNOCK = 0.05
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
Matter.Body.setVelocity(player, {
x: player.velocity.x * 0.8,
y: player.velocity.y * 0.8
});
}
} else {
if (Math.abs(player.velocity.x) < 12) player.force.x -= 0.04 * Math.cos(m.angle)
player.force.y -= 0.01 * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
}
}, },
fireNormal() { fireNormal() {
if (this.nextFireCycle + 1 < m.cycle) this.startingHoldCycle = m.cycle //reset if not constantly firing if (this.nextFireCycle + 1 < m.cycle) this.startingHoldCycle = m.cycle //reset if not constantly firing
@@ -4118,21 +4153,98 @@ const b = {
} }
}; };
b.muzzleFlash(30); b.muzzleFlash(30);
//very complex recoil system
if (m.onGround) {
if (input.down) {
const KNOCK = 0.01
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
} else {
const KNOCK = 0.02
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
}
} else {
const KNOCK = 0.01
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) * 0.5 //reduce knock back in vertical direction to stop super jumps
}
}, },
// fireNailFireRate() { fireRecoilRivets() {
// if (this.nextFireCycle + 1 < m.cycle) this.startingHoldCycle = m.cycle //reset if not constantly firing // m.fireCDcycle = m.cycle + Math.floor((input.down ? 25 : 17) * b.fireCDscale); // cool down
// const CD = Math.max(7.5 - 0.06 * (m.cycle - this.startingHoldCycle), 2) //CD scales with cycles fire is held down if (this.nextFireCycle + 1 < m.cycle) this.startingHoldCycle = m.cycle //reset if not constantly firing
// this.nextFireCycle = m.cycle + CD * b.fireCDscale //predict next fire cycle if the fire button is held down const CD = Math.max(30 - 0.15 * (m.cycle - this.startingHoldCycle), 8) //CD scales with cycles fire is held down
this.nextFireCycle = m.cycle + CD * b.fireCDscale //predict next fire cycle if the fire button is held down
m.fireCDcycle = m.cycle + Math.floor(CD * b.fireCDscale); // cool down
// m.fireCDcycle = m.cycle + Math.floor(CD * b.fireCDscale); // cool down const me = bullet.length;
// this.baseFire(m.angle + (Math.random() - 0.5) * (Math.random() - 0.5) * (input.down ? 1.35 : 3.2) / CD) const size = tech.rivetSize * 8
// }, bullet[me] = Bodies.rectangle(m.pos.x + 35 * Math.cos(m.angle), m.pos.y + 35 * Math.sin(m.angle), 5 * size, size, b.fireAttributes(m.angle));
bullet[me].dmg = tech.isNailRadiation ? 0 : 2.75
Matter.Body.setDensity(bullet[me], 0.002);
Composite.add(engine.world, bullet[me]); //add bullet to world
const SPEED = input.down ? 60 : 50
Matter.Body.setVelocity(bullet[me], {
x: SPEED * Math.cos(m.angle),
y: SPEED * Math.sin(m.angle)
});
bullet[me].endCycle = simulation.cycle + 180
bullet[me].beforeDmg = function(who) { //beforeDmg is rewritten with ice crystal tech
if (tech.isNailCrit && !who.shield && Vector.dot(Vector.normalise(Vector.sub(who.position, this.position)), Vector.normalise(this.velocity)) > 0.94) {
b.explosion(this.position, 300 + 30 * Math.random()); //makes bullet do explosive damage at end
}
if (tech.isNailRadiation) mobs.statusDoT(who, 7 * (tech.isFastRadiation ? 0.7 : 0.24), tech.isSlowRadiation ? 360 : (tech.isFastRadiation ? 60 : 180)) // one tick every 30 cycles
};
bullet[me].minDmgSpeed = 10
bullet[me].frictionAir = 0.006;
bullet[me].do = function() {
this.force.y += this.mass * 0.0008
//rotates bullet to face current velocity?
if (this.speed > 7) {
const facing = {
x: Math.cos(this.angle),
y: Math.sin(this.angle)
}
const mag = 0.002 * this.mass
if (Vector.cross(Vector.normalise(this.velocity), facing) < 0) {
this.torque += mag
} else {
this.torque -= mag
}
}
};
b.muzzleFlash(30);
//very complex recoil system
if (m.onGround) {
if (input.down) {
const KNOCK = 0.05
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
Matter.Body.setVelocity(player, {
x: player.velocity.x * 0.4,
y: player.velocity.y * 0.4
});
} else {
const KNOCK = 0.15
player.force.x -= KNOCK * Math.cos(m.angle)
player.force.y -= KNOCK * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
Matter.Body.setVelocity(player, {
x: player.velocity.x * 0.7,
y: player.velocity.y * 0.7
});
}
} else {
if (Math.abs(player.velocity.x) < 12) player.force.x -= 0.1 * Math.cos(m.angle)
player.force.y -= 0.03 * Math.sin(m.angle) //reduce knock back in vertical direction to stop super jumps
}
},
fireInstantFireRate() { fireInstantFireRate() {
m.fireCDcycle = m.cycle + Math.floor(2 * b.fireCDscale); // cool down m.fireCDcycle = m.cycle + Math.floor(2 * b.fireCDscale); // cool down
this.baseFire(m.angle + (Math.random() - 0.5) * (Math.random() - 0.5) * (input.down ? 1.35 : 3.2) / 2) this.baseFire(m.angle + (Math.random() - 0.5) * (Math.random() - 0.5) * (input.down ? 1.35 : 3.2) / 2)
}, },
baseFire(angle) { baseFire(angle, speed = 30 + 6 * Math.random()) {
const speed = 30 + 6 * Math.random()
b.nail({ b.nail({
x: m.pos.x + 30 * Math.cos(m.angle), x: m.pos.x + 30 * Math.cos(m.angle),
y: m.pos.y + 30 * Math.sin(m.angle) y: m.pos.y + 30 * Math.sin(m.angle)

View File

@@ -17,7 +17,9 @@ const level = {
// simulation.isHorizontalFlipped = true // simulation.isHorizontalFlipped = true
// m.setField("plasma torch") // m.setField("plasma torch")
// b.giveGuns("nail gun") // b.giveGuns("nail gun")
// tech.giveTech("negative friction") // tech.giveTech("rotary cannon")
// tech.giveTech("pneumatic actuator")
// tech.giveTech("rivet gun")
// for (let i = 0; i < 2; i++) tech.giveTech("refractory metal") // for (let i = 0; i < 2; i++) tech.giveTech("refractory metal")
// tech.giveTech("all-stars") // tech.giveTech("all-stars")
// for (let i = 0; i < 3; i++) tech.giveTech("overcharge") // for (let i = 0; i < 3; i++) tech.giveTech("overcharge")
@@ -2291,7 +2293,7 @@ const level = {
// for (let i = 0; i < 200; i++) powerUps.directSpawn(710 + 1000 * Math.random(), -710 + 1000 * Math.random(), "tech"); // for (let i = 0; i < 200; i++) powerUps.directSpawn(710 + 1000 * Math.random(), -710 + 1000 * Math.random(), "tech");
spawn.mapRect(2500, -1200, 200, 750); //right wall spawn.mapRect(2500, -1200, 200, 750); //right wall
blockDoor(2585, -210) // blockDoor(2585, -210)
spawn.mapRect(2500, -200, 200, 300); //right wall spawn.mapRect(2500, -200, 200, 300); //right wall
spawn.mapRect(4500, -1200, 200, 650); //right wall spawn.mapRect(4500, -1200, 200, 650); //right wall
blockDoor(4585, -310) blockDoor(4585, -310)
@@ -2307,9 +2309,9 @@ const level = {
spawn.mapRect(5300, -275, 50, 175); spawn.mapRect(5300, -275, 50, 175);
spawn.mapRect(5050, -100, 50, 150); spawn.mapRect(5050, -100, 50, 150);
spawn.mapRect(4850, -275, 50, 175); spawn.mapRect(4850, -275, 50, 175);
// level.difficultyIncrease(30) //30 is near max on hard //60 is near max on why level.difficultyIncrease(40) //30 is near max on hard //60 is near max on why
// spawn.starter(1900, -500, 200) //big boy spawn.starter(1900, -500, 200) //big boy
spawn.blockGroup(1900, -500) // spawn.blockGroup(1900, -500)
// for (let i = 0; i < 10; ++i) spawn.bodyRect(1600 + 5, -500, 30, 40); // for (let i = 0; i < 10; ++i) spawn.bodyRect(1600 + 5, -500, 30, 40);
// spawn.laserBombingBoss(1900, -500) // spawn.laserBombingBoss(1900, -500)
// for (let i = 0; i < 5; i++) spawn.focuser(1900, -500) // for (let i = 0; i < 5; i++) spawn.focuser(1900, -500)

View File

@@ -42,6 +42,11 @@ const spawn = {
const pick = this.pickList[Math.floor(Math.random() * this.pickList.length)]; const pick = this.pickList[Math.floor(Math.random() * this.pickList.length)];
this[pick](x, y); this[pick](x, y);
} }
if (tech.isMoreMobs) {
const pick = this.pickList[Math.floor(Math.random() * this.pickList.length)];
this[pick](x, y);
}
}, },
randomSmallMob(x, y, randomSmallMob(x, y,
num = Math.max(Math.min(Math.round(Math.random() * simulation.difficulty * 0.2), 4), 0), num = Math.max(Math.min(Math.round(Math.random() * simulation.difficulty * 0.2), 4), 0),
@@ -53,6 +58,12 @@ const spawn = {
this[pick](x + Math.round((Math.random() - 0.5) * 20) + i * size * 2.5, y + Math.round((Math.random() - 0.5) * 20), size); this[pick](x + Math.round((Math.random() - 0.5) * 20) + i * size * 2.5, y + Math.round((Math.random() - 0.5) * 20), size);
} }
} }
if (tech.isMoreMobs) {
for (let i = 0; i < num; ++i) {
const pick = this.pickList[Math.floor(Math.random() * this.pickList.length)];
this[pick](x + Math.round((Math.random() - 0.5) * 20) + i * size * 2.5, y + Math.round((Math.random() - 0.5) * 20), size);
}
}
}, },
randomGroup(x, y, chance = 1) { randomGroup(x, y, chance = 1) {
if (spawn.spawnChance(chance) && simulation.difficulty > 2 || chance === Infinity) { if (spawn.spawnChance(chance) && simulation.difficulty > 2 || chance === Infinity) {

View File

@@ -3670,45 +3670,6 @@
} }
} }
}, },
{
name: "needle gun",
description: "<strong>nail gun</strong> fires <strong>3</strong> mob piercing <strong>needles</strong><br>requires <strong>3</strong> times more <strong>bullets</strong>",
isGunTech: true,
maxCount: 1,
count: 0,
frequency: 2,
frequencyDefault: 2,
allowed() {
return tech.haveGunCheck("nail gun") && !tech.nailInstantFireRate && !tech.isIceCrystals && !tech.isRivets
},
requires: "nail gun, not ice crystal, rivets, or pneumatic actuator",
effect() {
tech.isNeedles = true
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
if (b.guns[i].name === "nail gun") {
b.guns[i].ammo = Math.ceil(b.guns[i].ammo / 3);
b.guns[i].ammoPack = Math.ceil(b.guns[i].defaultAmmoPack / 3);
b.guns[i].chooseFireMethod()
simulation.updateGunHUD();
break
}
}
},
remove() {
if (tech.isNeedles) {
tech.isNeedles = false
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
if (b.guns[i].name === "nail gun") {
b.guns[i].chooseFireMethod()
b.guns[i].ammo = Math.ceil(b.guns[i].ammo * 3);
b.guns[i].ammoPack = b.guns[i].defaultAmmoPack;
simulation.updateGunHUD();
break
}
}
}
}
},
{ {
name: "needle ice", name: "needle ice",
description: `when <strong>needles</strong> impact walls<br>they chip off <strong>1-2</strong> freezing <strong class='color-s'>ice IX</strong> crystals`, description: `when <strong>needles</strong> impact walls<br>they chip off <strong>1-2</strong> freezing <strong class='color-s'>ice IX</strong> crystals`,
@@ -3747,6 +3708,45 @@
tech.isNeedleShieldPierce = false tech.isNeedleShieldPierce = false
} }
}, },
{
name: "needle gun",
description: "<strong>nail gun</strong> fires <strong>3</strong> mob piercing <strong>needles</strong><br>requires <strong>3</strong> times more <strong>bullets</strong>",
isGunTech: true,
maxCount: 1,
count: 0,
frequency: 2,
frequencyDefault: 2,
allowed() {
return tech.haveGunCheck("nail gun") && !tech.nailInstantFireRate && !tech.isIceCrystals && !tech.isRivets && !tech.nailRecoil
},
requires: "nail gun, not ice crystal, rivets, or pneumatic actuator",
effect() {
tech.isNeedles = true
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
if (b.guns[i].name === "nail gun") {
b.guns[i].ammo = Math.ceil(b.guns[i].ammo / 3);
b.guns[i].ammoPack = Math.ceil(b.guns[i].defaultAmmoPack / 3);
b.guns[i].chooseFireMethod()
simulation.updateGunHUD();
break
}
}
},
remove() {
if (tech.isNeedles) {
tech.isNeedles = false
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
if (b.guns[i].name === "nail gun") {
b.guns[i].chooseFireMethod()
b.guns[i].ammo = Math.ceil(b.guns[i].ammo * 3);
b.guns[i].ammoPack = b.guns[i].defaultAmmoPack;
simulation.updateGunHUD();
break
}
}
}
}
},
{ {
name: "rivet gun", name: "rivet gun",
description: "<strong>nail gun</strong> slowly fires a heavy <strong>rivet</strong>", description: "<strong>nail gun</strong> slowly fires a heavy <strong>rivet</strong>",
@@ -3847,9 +3847,9 @@
frequency: 2, frequency: 2,
frequencyDefault: 2, frequencyDefault: 2,
allowed() { allowed() {
return tech.haveGunCheck("nail gun") && !tech.isRivets && !tech.isNeedles return tech.haveGunCheck("nail gun") && !tech.isRivets && !tech.isNeedles && !tech.nailRecoil
}, },
requires: "nail gun, not rivets or needles", requires: "nail gun, not rotary cannon, rivets, or needles",
effect() { effect() {
tech.nailInstantFireRate = true tech.nailInstantFireRate = true
for (i = 0, len = b.guns.length; i < len; i++) { //find which gun for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
@@ -3865,33 +3865,33 @@
} }
} }
}, },
// { {
// name: "powder-actuated", name: "rotary cannon",
// description: "<strong>nail gun</strong> takes <strong>no</strong> time to ramp up<br>nails have a <strong>30%</strong> faster muzzle <strong>speed</strong>", description: "<strong>nail gun</strong> has increased muzzle <strong>speed</strong>,<br>maximum <strong>fire rate</strong>, <strong>accuracy</strong>, and <strong>recoil</strong>",
// isGunTech: true, isGunTech: true,
// maxCount: 1, maxCount: 1,
// count: 0, count: 0,
// frequency: 2, frequency: 2,
// frequencyDefault: 2, frequencyDefault: 2,
// allowed() { allowed() {
// return tech.haveGunCheck("nail gun") && tech.nailFireRate && !tech.isIceCrystals return tech.haveGunCheck("nail gun") && !tech.nailInstantFireRate
// }, },
// requires: "nail gun and pneumatic actuator not ice crystal nucleation", requires: "nail gun, not pneumatic actuator",
// effect() { effect() {
// tech.nailInstantFireRate = true tech.nailRecoil = true
// for (i = 0, len = b.guns.length; i < len; i++) { //find which gun for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
// if (b.guns[i].name === "nail gun") b.guns[i].chooseFireMethod() if (b.guns[i].name === "nail gun") b.guns[i].chooseFireMethod()
// } }
// }, },
// remove() { remove() {
// if (tech.nailInstantFireRate) { if (tech.nailRecoil) {
// tech.nailInstantFireRate = false tech.nailRecoil = false
// for (i = 0, len = b.guns.length; i < len; i++) { //find which gun for (i = 0, len = b.guns.length; i < len; i++) { //find which gun
// if (b.guns[i].name === "nail gun") b.guns[i].chooseFireMethod() if (b.guns[i].name === "nail gun") b.guns[i].chooseFireMethod()
// } }
// } }
// } }
// }, },
{ {
name: "supercritical fission", name: "supercritical fission",
description: "<strong>nails</strong>, <strong>needles</strong>, and <strong>rivets</strong> can <strong class='color-e'>explode</strong><br>if they strike mobs near their <strong>center</strong>", description: "<strong>nails</strong>, <strong>needles</strong>, and <strong>rivets</strong> can <strong class='color-e'>explode</strong><br>if they strike mobs near their <strong>center</strong>",
@@ -6776,6 +6776,25 @@
tech.removeMaxHealthOnKill = 0 tech.removeMaxHealthOnKill = 0
} }
}, },
{
name: "-parthenocarpy-",
description: "<strong style='color: #f55;'>experiment:</strong> spawn about 50% more mobs",
maxCount: 1,
count: 1,
frequency: 0,
isBadRandomOption: true,
isExperimentalMode: true,
allowed() {
return build.isExperimentSelection
},
requires: "",
effect() {
tech.isMoreMobs = true
},
remove() {
tech.isMoreMobs = false
}
},
//************************************************** //**************************************************
//************************************************** JUNK //************************************************** JUNK
//************************************************** tech //************************************************** tech
@@ -6800,7 +6819,7 @@
// }, // },
{ {
name: "negative friction", name: "negative friction",
description: "when you touch walls you speed up instead of slowing down. It's actually pretty cool, seriously.", description: "when you touch walls you speed up instead of slowing down. It's kinda fun.",
maxCount: 1, maxCount: 1,
count: 0, count: 0,
frequency: 0, frequency: 0,
@@ -6811,7 +6830,7 @@
}, },
requires: "", requires: "",
effect() { effect() {
player.friction = -0.5 player.friction = -0.4
}, },
remove() { remove() {
if (this.count) player.friction = 0.002 if (this.count) player.friction = 0.002
@@ -8624,5 +8643,7 @@
cloakDuplication: null, cloakDuplication: null,
extruderRange: null, extruderRange: null,
isRodAreaDamage: null, isRodAreaDamage: null,
isForeverDrones: null isForeverDrones: null,
isMoreMobs: null,
nailRecoil: null
} }

View File

@@ -1,13 +1,19 @@
******************************************************** NEXT PATCH ************************************************** ******************************************************** NEXT PATCH **************************************************
perimeter defense and network effect each give 1% more bonus per bot (around an 18% increase for each tech) tech: rotary cannon - nail gun (and rivet gun) have increased fire rate, muzzle speed, recoil, and accuracy
experiment -parthenocarpy- spawn about 50% more mobs
extra bosses spawned from parthenogenesis and apomixis have health increased by your duplication chance
(if you have 50% duplication the extra boss have 50% more health)
apomixis no longer costs 8 research
******************************************************** TODO ******************************************************** ******************************************************** TODO ********************************************************
minigun: tech for nail gun - Its ramp-up time must not be removable. Recoil should be intense, enough that the player cannot walk forward quickly while using it.
nail gun gains: accuracy, bullet speed, huge recoil, fire rate
alternative to pnumatic that stops ramp up
maybe try to also apply to rivets?
animate going to next level?
door fills in with color that climbs up vertically through the door graphic the longer you stand on door
hold crouch on door? or automatically
Plasma Burner: upgrade for plasma torch, basically just a jet engine. does high damage, but short range, mostly for player movement. Plasma Burner: upgrade for plasma torch, basically just a jet engine. does high damage, but short range, mostly for player movement.
maybe reduce gravity to really low then apply a vector away from mouse direction maybe reduce gravity to really low then apply a vector away from mouse direction