code:
App.Facilities.MasterSuite.masterSuite = class MasterSuite extends App.Facilities.Facility {
	constructor() {
		const masterSuite = App.Entity.facilities.masterSuite;
		const decommissionHandler = () => {
			V.masterSuite = 0;
			V.masterSuiteUpgradeLuxury = 0;
			V.masterSuitePregnancySlaveLuxuries = 0;
			V.masterSuiteDecoration = "standard";
			V.masterSuitePregnancyFertilityDrugs = 0;
			V.masterSuitePregnancyFertilitySupplements = 0;
			V.masterSuiteUpgradePregnancy = 0;
			V.masterSuiteHyperPregnancy = 0;
		};

		super(
			masterSuite,
			decommissionHandler,
		);

		V.nextButton = "Back to Main";
		V.nextLink = "Main";
		V.encyclopedia = "Master Suite";

		this.pregnantSlaves = 0;
		this.pregnantWithMultiples = 0;
		this.currentSlaves = App.Utils.sortedEmployees(App.Entity.facilities.masterSuite);

		if (S.Concubine && S.Concubine.pregKnown) {
			this.pregnantSlaves++;

			if (S.Concubine.pregType > 1) {
				this.pregnantWithMultiples++;
			}
		}

		for (const slave of this.currentSlaves) {
			if (slave.pregKnown) {
				this.pregnantSlaves++;

				if (slave.pregType > 1) {
					this.pregnantWithMultiples++;
				}
			}
		}
	}

	/** @returns {string} */
	get intro() {
		const text = [];

		const avg = App.Utils.masterSuiteAverages();

		text.push(`${this.facility.nameCaps} is furnished`, this.decorations);

		if (V.masterSuiteUpgradeLuxury === 1) {
			text.push(`It is full of luxuries of all kinds. The slaves here live free of want or worry, and have everything except their freedom. Their only duties are to please you and look after the suite and one another.`);

			if (this.currentSlaves.length > 2) {
				text.push(`It's busy with slaves, so many that they are able to rotate through keeping themselves perfect and ready for your pleasure. The slaves not on call at the moment are beautifying themselves, cleaning, or serving others.`);

				if (this.pregnantSlaves > 2 && this.pregnantWithMultiples < 2) {
					text.push(`Many of the slaves are pregnant, and they walk around proudly displaying their bellies and the new slaves growing inside them.`);
				} else if (this.pregnantWithMultiples > 2 && V.masterSuiteHyperPregnancy === 1) {
					text.push(`Many of the slaves are heavily pregnant with multiple children, and they waddle around proudly displaying their distended bulging bellies and the next generation of slaves growing within them.`);
				} else if (this.pregnantWithMultiples > 2) {
					text.push(`Many of the slaves are pregnant with multiple children, and they walk around proudly displaying their distended bellies and the next generation of slaves growing within them.`);
				}
			} else if (this.currentSlaves.length > 0) {
				text.push(`It's sparsely populated, so that the few slaves here have to work hard and quickly to ensure that an assortment of sex slaves is perfect and ready for your pleasure at any given moment.`);
			} else {
				text.push(`None of your slaves are serving here.`);
			}
		} else if (V.masterSuiteUpgradeLuxury === 2) {
			text.push(`The true focus of the suite is, however, the fuckpit. This stepped depression in the middle of the floor`);

			if (this.currentSlaves.length > 3) {
				text.push(`is filled by cushions and every slave in the suite who isn't sleeping, eating, or bathing.`);

				if (avg.energy > 90) {
					text.push(`They're having energetic group sex; most of them are fucking and being fucked at the same time.`);
				} else if (avg.energy > 60) {
					text.push(`They're having group sex; most of them are in active sexual contact with more than one partner.`);
				} else {
					text.push(`They're having languid group sex; more than one slave is dozing while another plays with their body.`);
				}
				if (avg.energy > 90) {
					text.push(`The pit features automated cleaning systems, which are quite necessary.`);

					if (avg.dick > 4) {
						text.push(`With so many huge cocks in the fuckpit, every hole available is frequently fucked vigorously.`);
					}

					if (avg.cum > 4) {
						text.push(`The slaves' bodies grow more coated with cum, and more of the white stuff drips from their holes, until they take a break for a shower.`);
					}

					if (avg.milk > 4000) {
						text.push(`Most of them cannot tear themselves away (or cannot escape) for a normal machine milking, so their tender, overfull breasts squirt milk whenever anyone touches them. The lowest level of the fuckpit is a pool of milk.`);
					}
				}

				if (this.pregnantSlaves > 2 && this.pregnantWithMultiples < 2) {
					text.push(`Many of the slaves are pregnant, and more than one has her face buried in the cunt directly below a gravid belly while she lovingly massages her own.`);
				} else if (this.pregnantWithMultiples > 2 && V.masterSuiteHyperPregnancy === 1) {
					text.push(`Many of the slaves are heavily pregnant with multiple children, and more than one has her face buried in the cunt directly below a massively overburdened belly while she lovingly massages her own distended squirming stomach.`);
				} else if (this.pregnantWithMultiples > 2) {
					text.push(`Many of the slaves are pregnant with multiple children, and more than one has her face buried in the cunt directly below a grossly swollen belly while she lovingly massages her own distended stomach.`);
				}
			} else if (this.currentSlaves.length > 0) {
				text.push(`has a few lonely-looking fucktoys in it, badly outnumbered by the cushions.`);
			} else {
				text.push(`is desolate and unpopulated.`);
			}
		} else {
			if (this.currentSlaves.length > 2) {
				text.push(`It's busy with slaves, so many that they are able to rotate through keeping themselves perfect and ready for your pleasure. The slaves not on call at the moment are beautifying themselves, cleaning, or serving others.`);

				if (this.pregnantSlaves > 2 && this.pregnantWithMultiples < 2) {
					text.push(`Many of the slaves are pregnant, and they walk around proudly displaying their bellies and the new slaves growing inside them.`);
				} else if (this.pregnantWithMultiples > 2 && V.masterSuiteHyperPregnancy === 1) {
					text.push(`Many of the slaves are heavily pregnant with multiple children, and they waddle around proudly displaying their distended bulging bellies and the next generation of slaves growing within them.`);
				} else if (this.pregnantWithMultiples > 2) {
					text.push(`Many of the slaves are pregnant with multiple children, and they walk around proudly displaying their distended bellies and the next generation of slaves growing within them.`);
				}
			} else if (this.currentSlaves.length > 0) {
				text.push(`It's sparsely populated, so that the few slaves here have to work hard and quickly to ensure that an assortment of sex slaves is perfect and ready for your pleasure at any given moment.`);
			} else {
				text.push(`None of your slaves are serving here.`);
			}
		}

		return text.join(' ');
	}

	/** @returns {string} */
	get decorations() {
		/** @type {FC.Facilities.Decoration} */
		let FS = null;

		if (V.masterSuiteUpgradeLuxury === 1) {
			FS = {
				"Roman Revivalist": `as a Roman emperor's apartment. There is a small shrine to the old gods the ${properMaster()} favors in a side room, and the flooring is erotic mosaic. Pride of place is given to a set of low couches placed together, capable of accommodating many nude bodies.`,
				"Neo-Imperialist": `as an apartment worthy of a modern-day Emperor. The highest of technology decorates every space, allowing you to remain in constant communication with the rest of the arcology - your fledgling empire - even when in your room. The ${properMaster()}'s suite is an elaborate shrine to your many victories, fitted with many low couches to fit a whole harem inside, and the banners of your house hang around you on every side. The centerpiece of your personal apartment is a massive tapestry, designed in ancient style and depicting the creation of your Arcology from the collapsing Old World, all the way up to the modern day, with you standing over a great cheering crowd in your golden crown. You wonder for a moment if you'll have to commission more tapestries as the Arcology advances further.`,
				"Aztec Revivalist": `as an Aztec cultural, spiritual and military leader of the city you're allowed great leniency. The ${properMaster()}'s room is created to gratify you as a true god of the people.`,
				"Egyptian Revivalist": `after the royal room of an ancient Egyptian palace. There is a small shrine to the old gods the ${properMaster()} favors in a side room, and linen hangings decorate the walls and ceiling. An imposing bed of sandalwood occupies the center of the room.`,
				"Edo Revivalist": `in the spartan style of an Edo period castle's innermost rooms. Rice paper screens partition off many small cubicles around its large central space. There, around a low bed, there are many mats for servants to kneel around their ${properMaster()}.`,
				"Arabian Revivalist": `as a beguiling haze of Arabian decadence. There is a great gilded bed in the center of the space, piled with silk pillows for naked bodies to recline on. Gauzy curtains flutter in the warm, heady breeze.`,
				"Chinese Revivalist": `as though it were the innermost sanctum of the Forbidden City. A massive bed fills the central space. The walls are gorgeous gilded hand-carved screens, and heavy jade statues of favored gods crouch in the corners.`,
				"Chattel Religionist": `as a severe place of cold stone and hard wood. A single shaft of sunlight illuminates an enormous stone platform that serves as a bed where penitents give their bodies to their ${properMaster()}.`,
				"Degradationist": `with a gothic grandeur. Blood-red upholstery and hardwood menace crouch in the center of the space in the form of a massive poster bed with curtains of chain mail.`,
				"Repopulationist": `comfortably, with lots of cushions and seats for pregnant slaves to lounge on. Various specialized toys, as well as, lotions and creams are readily available. There's a huge, reinforced, low to the ground bed in the middle of the suite.`,
				"Eugenics": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls lots of fun. There's a huge bed in the middle of the suite, with hidden compartments containing condoms and spermicides.`,
				"Asset Expansionist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with stacked slaves as fun as possible. There's a huge bed in the middle of the suite, heavily reinforced.`,
				"Transformation Fetishist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with bimbo slaves as fun as possible. There's a huge bed in the middle of the suite, heavily reinforced.`,
				"Gender Radicalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls in the butt lots of fun. There's a huge bed in the middle of the suite, with straps to restrain slave girls who don't want to be fucked in the butt, but they're concealed for now.`,
				"Gender Fundamentalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls nice and enjoyable. There's a huge bed in the middle of the suite, with straps to restrain slave girls who don't want to be fucked, but they're concealed for now.`,
				"Physical Idealist": `as a shrine to the owner's body. Athletic trophies and photographs of past victories line the walls. There's a huge bed in the middle of the space, and there are mirrors almost everywhere, including on the ceiling over the bed.`,
				"Supremacist": `like the royal bedroom in a palace in the old countries of ${V.arcologies[0].FSSupremacistRace} people. A massive four-poster bed dominates the space.`,
				"Subjugationist": `like the royal bedroom in a palace in the old countries which favored ${V.arcologies[0].FSSubjugationistRace} slaves. A massive four-poster bed dominates the space.`,
				"Paternalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Pastoralist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants. The space is dominated by a massive, reinforced bed, built in sections so that part of it can be cleaned while cream-squirting cows cavort on the rest.`,
				"Maturity Preferentialist": `comfortably, with elegant sex toys and perfumed lubricants designed to appeal to mature sex slaves. The space is dominated by a broad, soft bed, well supplied with pillows. It's the perfect place to relax with a harem of MILFs.`,
				"Youth Preferentialist": `comfortably, with pastel-colored sex toys and flavored lubricants designed to appeal to eager young sex slaves. The space is dominated by a broad, reinforced bed, without cushions or sheets, which would just get in the way of energetic sex.`,
				"Body Purist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable. The space is dominated by a huge bed with soft sheets.`,
				"Slimness Enthusiast": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable. The space is dominated by a huge bed with soft sheets.`,
				"Hedonistic": `comfortably, with lots of lounges for a hefty slaves to relax on. ${V.arcologies[0].FSHedonisticDecadenceResearch === 1 ? `Platters of food and treats are readily available throughout the room and are` : `Slave food is readily available for your harem and platters of food for yourself are`} never out of arm's reach. There's a huge, reinforced, low to the ground bed in the middle of the suite.`,
				"Intellectual Dependency": `comfortably, with lots of easy-to-clean leather and plentiful easy-to-use tools, toys, and lubricants to make sex with bimbo slaves as fun and simple as possible. There's a huge bed in the middle of the suite, heavily reinforced.`,
				"Slave Professionalism": `comfortably, with complex sex toys and tools designed to maximize pleasure when used by skilled hands. The space is dominated by a broad, soft bed, well supplied with pillows. The rest is dedicated to perfecting oneself and boosting ${properMaster()}'s status ever higher.`,
				"Petite Admiration": `comfortably, with plentiful tools, toys, lubricants and a bevy of stepping stools to accommodate even the shortest slave. There's a huge, reinforced, low to the ground bed in the middle of the suite.`,
				"Statuesque Glorification": `comfortably, though designed for slaves of the taller variety. Short slaves will find the furniture, and the room's centerpiece, a massive four-poster bed, woefully out of their reach.`,
				"standard": `in a refined, yet practical style. It's dominated by a huge bed in which many slaves could serve their ${properTitle()} and then cuddle afterward.`,
			};
		} else if (V.masterSuiteUpgradeLuxury === 2) {
			FS = {
				"Roman Revivalist": `as a Roman emperor's apartment. There is a small shrine to the old gods the ${properTitle()} favors in a side room, and the flooring is erotic mosaic.`,
				"Neo-Imperialist": `as an apartment worthy of a modern-day Emperor. The highest of technology decorates every space, allowing you to remain in constant communication with the rest of the arcology - your fledgling empire - even when in your room. The ${properMaster()}'s suite is an elaborate shrine to your many victories, fitted with a large bed with hanging golden bedposts, and the banners of your house hang around you on every side. The centerpiece of your personal apartment is a massive tapestry, designed in ancient style and depicting the creation of your Arcology from the collapsing Old World, all the way up to the modern day, with you standing over a great cheering crowd in your golden crown. You wonder for a moment if you'll have to commission more tapestries as the Arcology advances further.`,
				"Aztec Revivalist": `as an Aztec cultural, spiritual and military leader of the city you're allowed great leniency. The ${properTitle()}'s room is created to gratify you as a true god of the people.`,
				"Egyptian Revivalist": `after the royal room of an ancient Egyptian palace. There is a small shrine to the old gods the ${properTitle()} favors in a side room, and linen hangings decorate the walls and ceiling.`,
				"Edo Revivalist": `in the spartan style of an Edo period castle's innermost rooms. Rice paper screens partition off many small cubicles around its large central space.`,
				"Arabian Revivalist": `as a beguiling haze of Arabian decadence. Gauzy curtains flutter in the warm, heady breeze.`,
				"Chinese Revivalist": `as though it were the innermost sanctum of the Forbidden City. The walls are gorgeous gilded hand-carved screens, and heavy jade statues of favored gods crouch in the corners.`,
				"Chattel Religionist": `as a severe place of cold stone and hard wood. A single shaft of sunlight illuminates the central space.`,
				"Degradationist": `with a gothic grandeur. Blood-red upholstery and hardwood menace decorate the walls.`,
				"Repopulationist": `comfortably, with lots of cushions and seats for a pregnant slaves to lounge on. There are various specialized toys, as well as, lotions and creams readily available.`,
				"Eugenics": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls lots of fun. Condoms and spermicides are readily available throughout the suite.`,
				"Asset Expansionist": `comfortably, with the convenience of massive-breasted slaves in mind. There are lots of handrails, cushions, and low tables, covered with creams, lubricants, and sex toys.`,
				"Transformation Fetishist": `comfortably, with the convenience of bimbos in mind. There are lots of makeup dressers with mirrors, stripper poles, and low tables, covered with creams, lubricants, and sex toys.`,
				"Gender Radicalist": `comfortably, with the convenience of dickgirls in mind. There are lots of makeup dressers with mirrors, stripper poles, and low tables, covered with creams, lubricants, and vibrating butt plugs.`,
				"Gender Fundamentalist": `comfortably, with the convenience and pleasure of slavegirls in mind. There are lots of makeup dressers with mirrors, soft divans, and low tables, covered with creams, lubricants, and vibrators.`,
				"Physical Idealist": `as a shrine to the owner's body. Athletic trophies and photographs of past victories line the walls. The entire area is filled with the heady odors of sweat, metabolites, and sex.`,
				"Supremacist": `like the royal bedroom in a palace in the old countries of ${V.arcologies[0].FSSupremacistRace} people.`,
				"Subjugationist": `like the royal bedroom in a palace in the old countries which favored ${V.arcologies[0].FSSubjugationistRace} slaves.`,
				"Paternalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Pastoralist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants, with a distinct focus on mammary intercourse.`,
				"Maturity Preferentialist": `comfortably, with elegant sex toys and perfumed lubricants designed to appeal to mature sex slaves.`,
				"Youth Preferentialist": `comfortably, with pastel-colored sex toys and flavored lubricants designed to appeal to eager young sex slaves.`,
				"Body Purist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Slimness Enthusiast": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Hedonistic": `comfortably, with lots of lounges for a hefty slaves to relax on. ${V.arcologies[0].FSHedonisticDecadenceResearch === 1 ? `Platters of food and treats are readily available throughout the room and are` : `Slave food is readily available for your harem and platters of food for yourself are`} never out of arm's reach.`,
				"Intellectual Dependency": `comfortably, with lots of easy-to-clean leather and plentiful easy-to-use tools, toys, and lubricants to make sex with bimbo slaves as fun and simple as possible.`,
				"Slave Professionalism": `comfortably, with complex sex toys and tools designed to maximize pleasure when used by skilled hands. The space is largely dedicated to perfecting oneself and boosting ${properMaster()}'s status ever higher.`,
				"Petite Admiration": `comfortably, with plentiful tools, toys, lubricants and a bevy of stepping stools to accommodate even the shortest slave.`,
				"Statuesque Glorification": `comfortably, though designed for slaves of the taller variety. Short slaves will find the furniture woefully out of their reach.`,
				"standard": `in a refined, yet practical style.`,
			};
		} else {
			FS = {
				"Roman Revivalist": `as a Roman patrician's apartment. There is a small shrine to the old gods the ${properTitle()} favors in a side room, and the flooring is erotic mosaic.`,
				"Neo-Imperialist": `as an apartment worthy of a modern-day King. The highest of technology decorates every space, allowing you to remain in constant communication with the rest of the arcology - your fledgling empire - even when in your room. The ${properMaster()}'s suite is an elaborate shrine to your many victories, fitted with a king-sized pod-bed, and the banners of your house hang around you on every side. The centerpiece of your personal apartment is a massive tapestry, designed in ancient style and depicting the creation of your Arcology from the collapsing Old World, all the way up to the modern day, with you standing over a great cheering crowd in your golden crown. You wonder for a moment if you'll have to commission more tapestries as the Arcology advances further.`,
				"Aztec Revivalist": `as an Aztec cultural, spiritual and military leader of the city you're allowed great leniency. The ${properTitle()}'s room is created to gratify you as a true god of the people.`,
				"Egyptian Revivalist": `after the best room of an ancient Egyptian mansion. There is a small shrine to the old gods the ${properTitle()} favors in a side room, and linen hangings decorate the walls and ceiling.`,
				"Edo Revivalist": `in the spartan style of an Edo period mansion's innermost rooms. Rice paper screens divide it into subsections, each of which contains little more than a low bed.`,
				"Arabian Revivalist": `as a beguiling haze of Arabian decadence. Soft cushions are scattered across the floor and piled against the walls to provide something for dusky, naked bodies to recline on. Gauzy curtains partition the room into a number of cozy dens.`,
				"Chinese Revivalist": `like the mansion of a senior mandarin of ancient China. The walls are gorgeous hand-carved wooden screens, and heavy jade statues of favored gods crouch in the corners.`,
				"Chattel Religionist": `as a severe place of cold stone and hard wood. A single shaft of sunlight illuminates the bed where penitents give their bodies to their ${properTitle()}.`,
				"Repopulationist": `comfortably, with lots of cushions and seats for a pregnant slaves to lounge on. Various specialized toys, as well as, lotions and creams are readily available.`,
				"Eugenics": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls lots of fun. Condoms and spermicides are readily available throughout the suite.`,
				"Degradationist": `with a gothic grandeur. Blood-red upholstery and hardwood menace. There are numerous places where resistant slaves can be restrained.`,
				"Asset Expansionist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with stacked slaves as fun as possible.`,
				"Transformation Fetishist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with bimbo slaves as fun as possible.`,
				"Gender Radicalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls in the butt lots of fun. The straps to restrain slave girls who don't want to be fucked in the butt are concealed for now.`,
				"Gender Fundamentalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make fucking slave girls nice and enjoyable. The straps to restrain slave girls who don't want to be fucked are concealed for now.`,
				"Physical Idealist": `as a shrine to the owner's body. Athletic trophies and photographs of past victories line the walls. There are mirrors almost everywhere, including on the ceiling over the bed.`,
				"Supremacist": `like the master bedroom in a mansion in the old countries of ${V.arcologies[0].FSSupremacistRace} people.`,
				"Subjugationist": `like the master bedroom in a mansion in the old countries which favored ${V.arcologies[0].FSSubjugationistRace} slaves.`,
				"Paternalist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Pastoralist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants. Everything that isn't waterproof is covered in plastic, to catch errant milk.`,
				"Maturity Preferentialist": `comfortably, with elegant sex toys and perfumed lubricants designed to appeal to mature sex slaves.`,
				"Youth Preferentialist": `comfortably, with pastel-colored sex toys and flavored lubricants designed to appeal to eager young sex slaves.`,
				"Body Purist": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Slimness Enthusiast": `comfortably, with lots of easy-to-clean leather and plentiful tools, toys, and lubricants to make sex with slaves mutually enjoyable.`,
				"Hedonistic": `comfortably, with lots of lounges for a hefty slaves to relax on. ${V.arcologies[0].FSHedonisticDecadenceResearch === 1 ? `Platters of food and treats are readily available throughout the room and are` : `Slave food is readily available for your harem and platters of food for yourself are`} never out of arm's reach.`,
				"Intellectual Dependency": `comfortably, with lots of easy-to-clean leather and plentiful easy-to-use tools, toys, and lubricants to make sex with bimbo slaves as fun and simple as possible.`,
				"Slave Professionalism": `comfortably, with complex sex toys and tools designed to maximize pleasure when used by skilled hands. The space is largely dedicated to perfecting oneself and boosting ${properMaster()}'s status ever higher.`,
				"Petite Admiration": `comfortably, with plentiful tools, toys, lubricants and a bevy of stepping stools to accommodate even the shortest slave.`,
				"Statuesque Glorification": `comfortably, though designed for slaves of the taller variety. Short slaves will find the furniture woefully out of their reach.`,
				"standard": `comfortably, as a fairly normal luxury suite. It is unusually large, to accommodate as large a stable of sex slaves as strikes your fancy.`,
			};
		}

		const res = FS[V.masterSuiteDecoration];

		if (!res) {
			throw new Error(`Unknown V.masterSuiteDecoration value of '${V.masterSuiteDecoration}' found in decorations().`);
		}

		return res;
	}

	/** @returns {FC.Facilities.Expand} */
	get expand() {
		return {
			amount: 2,
			desc: `${capFirstChar(V.masterSuiteName)} has room for ${numberWithPluralOne(V.masterSuite, "slave")} to live comfortably${V.masterSuiteUpgradeLuxury === 2
				? ` in the moments when they're not in the fuckpit`
				: V.masterSuiteUpgradeLuxury === 1 ? ` on its huge bed` : ``}. There ${this.facility.hostedSlaves === 1 ? `is ${num(this.facility.hostedSlaves)} slaves` : `are ${num(this.facility.hostedSlaves)} slave`} in ${V.masterSuiteName}.`,
			removeSlave: "please you",
		};
	}

	/** @returns {FC.IUpgrade[]} */
	get upgrades() {
		return [
			{
				property: "masterSuiteUpgradeLuxury",
				tiers: [
					{
						value: 0,
						upgraded: 1,
						text: `The master suite is a fairly standard room, albeit a much larger and more luxurious one.`,
						link: `Refit the suite to the height of traditional opulence`,
						cost: V.masterSuiteUpgradeLuxury === 0
							? 25000 * V.upgradeMultiplierArcology
							: 10000 * V.upgradeMultiplierArcology,
						handler: () => V.PC.skill.engineering += .1,
						note: ` and will focus the suite on you`,
					},
					{
						value: 1,
						text: `The large bed in the center of the room has been replaced with one that is nothing short of massive.`,
					},
					{
						value: 0,
						upgraded: 2,
						text: ``,
						link: `Remodel the suite around a luxurious pit for group sex`,
						cost: V.masterSuiteUpgradeLuxury === 0
							? 25000 * V.upgradeMultiplierArcology
							: 10000 * V.upgradeMultiplierArcology,
						handler: () => V.PC.skill.engineering += .1,
						note: ` and will encourage fucktoys to fuck each other`,
					},
					{
						value: 2,
						text: `A large, recessed space has been built in the center of the room where slaves can spend their days fucking each other.`,
					},
				],
			},
			{
				property: "masterSuiteUpgradePregnancy",
				tiers: [
					{
						value: 0,
						upgraded: 1,
						text: `The master suite does not currently have special customizations to support slave pregnancy.`,
						link: `Refit the suite to support and encourage slave pregnancy`,
						cost: 15000 * V.upgradeMultiplierArcology,
						handler: () => {
							V.PC.skill.engineering += .1;

							App.UI.reload();
						},
						prereqs: [
							() => !!V.seePreg,
						],
					},
					{
						value: 1,
						text: `The master suite has been further upgraded to support fertile slaves and encourage slave pregnancy, providing additional rest areas, better access to amenities, and a dedicated birthing chamber.`,
					},
				],
			},
		];
	}

	/** @returns {FC.Facilities.Rule[]} */
	get rules() {
		return [
			{
				property: "masterSuitePregnancySlaveLuxuries",
				prereqs: [
					() => V.masterSuiteUpgradePregnancy > 0,
				],
				options: [
					{
						get text() {
							return `Pregnant slaves have no extra luxuries to reduce stress.`;
						},
						link: `Normal duties`,
						value: 0,
					},
					{
						get text() {
							return `Pregnant slaves are being given some luxuries to reduce stress.`;
						},
						link: `Lighter duties`,
						value: 1,
					},
				],
			},
			{
				property: "masterSuitePregnancyFertilityDrugs",
				prereqs: [],
				options: [
					{
						get text() {
							return `Fertile slaves are not being given fertility drugs.`;
						},
						link: `No fertility drugs`,
						value: 0,
					},
					{
						get text() {
							return `Fertile slaves are being given fertility drugs, encouraging impregnation and multiple pregnancy.`;
						},
						link: `Standard fertility drugs`,
						value: 1,
					},
				],
			},
			{
				property: "masterSuiteHyperPregnancy",
				prereqs: [
					() => V.masterSuitePregnancyFertilityDrugs > 0,
				],
				options: [
					{
						get text() {
							return `Fertile slaves are not being given super fertility drugs.`;
						},
						link: `No super fertility drugs`,
						value: 0,
					},
					{
						get text() {
							return `Fertile slaves are being given super fertility drugs, encouraging impregnation and multiple pregnancy.`;
						},
						link: `Super fertility drugs`,
						value: 1,
					},
				],
			},
			{
				property: "masterSuitePregnancyFertilitySupplements",
				prereqs: [
					() => V.masterSuitePregnancyFertilityDrugs === 1 || V.masterSuiteHyperPregnancy === 1,
				],
				options: [
					{
						get text() {
							return `Fertile slaves are not being given fertility drug supplements.`;
						},
						link: `No supplements`,
						value: 0,
					},
					{
						get text() {
							return `Fertile slaves are being given supplements to their fertility drugs, further enhancing the chances of multiple pregnancy.`;
						},
						link: `Fertility supplements`,
						value: 1,
					},
				],
			},
		];
	}
};


code:
App.Data.Facilities.masterSuite = {
	baseName: "masterSuite",
	genericName: "Master Suite",
	jobs: {
		fucktoy: {
			position: "fucktoy",
			assignment: Job.MASTERSUITE,
			publicSexUse: false,
			fuckdollAccepted: false
		}
	},
	defaultJob: "fucktoy",
	manager: {
		position: "concubine",
		positionAbbreviation: "C",
		assignment: Job.CONCUBINE,
		careers: [],
		skill: null,
		publicSexUse: false,
		fuckdollAccepted: false,
		broodmotherAccepted: true,
		shouldWalk: false,
		shouldHold: false,
		shouldSee: false,
		shouldHear: false,
		shouldTalk: false,
		shouldThink: false,
		requiredDevotion: 51
	},
	decorated: true
};

App.Entity.Facilities.MasterSuiteFuckToyJob = class extends App.Entity.Facilities.FacilitySingleJob {
	/**
	 * @override
	 * @returns {string}
	 * */
	get assignment() {
		return this.facility.name;
	}

	/**
	 * @param {App.Entity.SlaveState} slave
	 * @returns {string[]}
	 */
	checkRequirements(slave) {
		let r = super.checkRequirements(slave);
		if (!App.Entity.Facilities.Job._isBrokenEnough(slave, 20, -51, -21, -50)) {
			r.push(`${slave.slaveName} is not sufficiently broken for ${this.facility.name}.`);
		}

		return r;
	}
};

App.Entity.Facilities.ConcubineJob = class extends App.Entity.Facilities.ManagingJob {
	checkRequirements(slave) {
		let r = super.checkRequirements(slave);
		if (isAmputee(slave)) {
			r.push(`${slave.slaveName} can't serve as your Concubine without limbs.`);
		}
		return r;
	}
};

App.Entity.facilities.masterSuite = new App.Entity.Facilities.SingleJobFacility(
	App.Data.Facilities.masterSuite,
	{
		fucktoy: new App.Entity.Facilities.MasterSuiteFuckToyJob()
	},
	new App.Entity.Facilities.ConcubineJob()
);

repo_name: Pecanus/fc

license: mit


code:
App.Facilities.MatronSelect = function() {
	const f = document.createDocumentFragment();

	if (S.Matron) {
		f.append(`${SlaveFullName(S.Matron)} is working as your Matron, managing the nursery. `);
		f.append(App.UI.DOM.link("Remove Matron", () => {
			removeJob(S.Matron, Job.MATRON);
		},
		[], "Nursery"
		));
	} else {
		f.append(`No Matron assigned, appoint one from your devoted slaves.`);
	}

	f.append(App.UI.SlaveList.facilityManagerSelection(App.Entity.facilities.nursery, "Nursery"));
	return f;
};


code:
:: AC Dump

<<if (ndef $activeChild) || ($activeChild == 0)>>

	@@.red;ERROR:@@ AC Dump, activeChild invalid, returnTo is '$returnTo', previous passage was '<<print previous()>>'. Please report this.

	<<link "Continue">><<goto $returnTo>><</link>> | [[Go Back|previous()]]

<<else>>

	<<set _CL = $cribs.length, _ID = $activeChild.ID>>

	<<if $i >= 0 && $i < _CL && $cribs[$i].ID == _ID>> /* shortcut if $i is already pointing to this slave */
		<<set $cribs[$i] = $activeChild>>
	<<else>>
		<<set $i = $cribs.findIndex(function(s) { s.ID === _ID; })>> /* find $i if exists */
		<<if $i != -1>> /* not found, so new slave */
			@@.red;ERROR:@@ $activeChild.slaveName not found! Please report this.
		<<else>>
			<<set $cribs[$i] = $activeChild>>
		<</if>>
	<</if>>

	<<goto $returnTo>>

<</if>>


code:
:: Next Child In Line

<<silently>>

<<set $i = $cribs.findIndex(function(c) { return c.ID === $activeChild.ID; })>>
<<set $cribs[$i] = $activeChild>> /* save changes before switching */
<<if $i == $cribs.length - 1>>
	<<set $activeChild = $cribs[0]>>
	<<if $activeChild.actualAge < 3>>
		<<goto "Infant Interact">>
	<<else>>
		<<goto "Child Interact">>
	<</if>>
<<else>>
	<<set $activeChild = $cribs[$i+1]>>
	<<if $activeChild.actualAge < 3>>
		<<goto "Infant Interact">>
	<<else>>
		<<goto "Child Interact">>
	<</if>>
<</if>>

<</silently>>


code:
App.Facilities.Nursery.nursery = class Nursery extends App.Facilities.Facility {
	constructor() {
		const nursery = App.Entity.facilities.nursery;
		const decommissionHandler = () => {
			V.nursery = 0;
			V.nurseryDecoration = "standard";
			V.nurseryNannies = 0;
			V.nannyInfluence = 0;
			V.cribs = [];
		};

		super(
			nursery,
			decommissionHandler,
		);

		V.nextButton = "Back to Main";
		V.nextLink = "Main";
		V.encyclopedia = "Nursery";
	}

	/** @returns {string} */
	get intro() {
		// TODO: add in effects based on number of children hosted
		const text = [];

		text.push(this.facility.nameCaps, this.decorations);

		if (this.facility.hostedSlaves > 2) {
			text.push(`${this.facility.nameCaps} is bustling with activity. Nannies are busily moving about, feeding babies and changing diapers.`);
		} else if (this.facility.hostedSlaves > 0) {
			text.push(`${this.facility.nameCaps} is working steadily. Nannies are moving about, cleaning up and feeding hungry children.`);
		} else if (S.Matron) {
			text.push(`${S.Matron.slaveName} is alone in ${this.facility.name}, and keeps the place clean and looks after the children ${getPronouns(S.Matron).himself}.`);
		} else {
			text.push(`${this.facility.nameCaps} is empty and quiet.`);
		}

		return text.join(' ');
	}

	/** @returns {string} */
	get decorations() {
		/** @type {FC.Facilities.Decoration} */
		const FS = {
			"Roman Revivalist": `is run with the Roman dream in mind, with wide open windows exposing the babies to the elements. The sleek marble halls bring a sense of serenity and duty as wet nurses wander the halls.`,
			"Neo-Imperialist": `is modeled as an ultra high-tech nursing area, with omnipresent advanced machinery monitoring every heartbeat of the babies within, the soft glow of machines pulsating against the banners of your family crest lining the walls.`,
			"Aztec Revivalist": `is lined head to toe in illustrious Aztec gold. Tiny but notable subscripts lay in plaques to honor the mothers who died giving birth, the children of said mothers, alive or dead, are tirelessly watched over to tend to their every need.`,
			"Egyptian Revivalist": `is decorated by sleek, sandstone tablets, golden statues, and even grander Egyptian wall sculptures, many of them depicting the conception, birth, and raising of a child. Each babe is reverently wrapped in linen covers as they drift to sleep to the stories of mighty pharaohs and prosperous palaces.`,
			"Edo Revivalist": `is minimalist in nature, but the errant paintings of cherry blossoms and vibrant Japanese maples give a certain peaceful air as the caretakers do their duties.`,
			"Arabian Revivalist": `is decorated wall to wall with splendorous carvings and religious Hamsas meant to protect the fostering children.`,
			"Chinese Revivalist": `is ripe with Chinese spirit. Depictions of colorful dragons and oriental designs grace the halls, rooms, and cribs of the babies who reside inside.`,
			"Chattel Religionist": `is decorated with childish religious cartoons and artistic tapestries of slaves bowing in submission, their themes always subsiding varying degrees of sexual worship. The caretakers that wander the halls obediently wear their habits, and never waste a moment to tenderly lull the children to sleep with stories of their prophet.`,
			"Degradationist": `is bare and sullen. The cries of the neglected children destined for slavery trying to find comfort in their burlap coverings echo the halls, while those that await freedom are raised among luxury and are taught to look down on their less fortunate peers.`,
			"Repopulationist": `is designed to be very open and public; a showing testament to your arcology's repopulation efforts. For those old enough to support them, they are strapped with big, but body warming, empathy bellies as to remind them of their destiny.`,
			"Eugenics": `is of utmost quality without a single pleasantry missing — if the parents are of the elite blood of course. While there are rare stragglers of unworthy genes, the child populace overall is pampered with warm rooms and plentiful small toys.`,
			"Asset Expansionist": `is not so much decorated as it is intelligently staffed. Every passerby, slave or not, burns the image of their jiggling asses and huge, wobbling tits into the minds of the children.`,
			"Transformation Fetishist": `is kept simple and clean. From their toys down to the nursemaids, the babies are exposed to the wonders of body transformation whenever possible.`,
			"Gender Radicalist": `is decorated by cheery cartoon depictions of slaves of many shapes, sizes, and genitals, all of them undeniably feminine. The elated smiles and yips of the nurses getting reamed constantly instill the appreciation of nice, pliable buttholes.`,
			"Gender Fundamentalist": `is simply designed and painted with soft feminine colors. The staff heavily encourage the children to play dress up and house, subtly sculpting their minds to proper gender norms and properly put them in line if they try to do otherwise.`,
			"Physical Idealist": `is furnished with kiddy health books and posters; their caretakers making painstakingly sure that the importance is drilled into their heads at a young age. Their food is often littered with vitamins and supplements to keep the children growing strong.`,
			"Supremacist": `is designed and structured to give those of ${V.arcologies[0].FSSupremacistRace} ethnicity the limelight of the nursery, while the others stay sectioned off and neglected to the world.`,
			"Subjugationist": `is made to foster and raise the young children of ${V.arcologies[0].FSSubjugationistRace} ethnicity. They are reminded of their place with every failure and are encouraged to submissively follow their stereotypes at a ripe young age.`,
			"Paternalist": `is well-stocked and by Paternalistic customs, constantly swaddle the children with love and attention. With the warm colors and sound of child laughter, to the untrained eye, the children actually seem free.`,
			"Pastoralist": `is decorated to make the children grow up thinking that a life focused on breast milk, cum, and other human secretions are part of the norm. The milky tits swaying above their cow-patterned cribs certainly help with that.`,
			"Maturity Preferentialist": `decorations remind the kids to respect those curvy and mature. The older nurserymaids are always flattered whenever the children try to act like adults and take care of the younger toddlers for them.`,
			"Youth Preferentialist": `is making young children the center of attention, their rooms supplied with plenty of toys, blankets, and surrogate mothers at their beck and call.`,
			"Body Purist": `is decorated to be very clean cut and sterilized with perfect corners and curves; symbolic of the human figure. Nursery maids are encouraged to show off their natural assets to show the children what the appropriate body should be.`,
			"Slimness Enthusiast": `constantly encourages the kids to try and keep their slim and cute physiques. They are given perfectly metered meals to make this possible.`,	// TODO: tie this in to food system
			"Hedonistic": `would make any toddler drool in amazement. Meals and naps every other hour, cribs stalked with toys and blankets, and plush slaves carry them to and fro without preamble. A delicious layer of baby fat is the ideal figure of a baby, and they couldn't be happier.`,
			"Intellectual Dependency": ``,	// TODO:
			"Slave Professionalism": ``,	// TODO:
			"Petite Admiration": `has large photos and paintings on the walls depicting small, petite children enjoying ${this.facility.name}'s amenities and having fun together.`,
			"Statuesque Glorification": `has large photos and paintings on the walls depicting tall children enjoying ${this.facility.name}'s amenities and having fun together.`,
			"standard": `is as comfortable and child-friendly as it needs to be. They have everything they need to grow into a proper slave.`,
		};

		const res = FS[V.nurseryDecoration];

		if (!res) {
			throw new Error(`Unknown V.nurseryDecoration value of '${V.nurseryDecoration}' found in decorations().`);
		}

		return res;
	}

	/** @returns {FC.Facilities.Expand} */
	get expand() {
		const slaves = this.facility.hostedSlaves;
		const nannies = numberWithPluralOne(V.nurseryNannies, 'nanny', 'nannies');

		return {
			amount: 1,
			desc: `${this.facility.nameCaps} has room to support ${nannies}. There ${slaves === 1 ? `is` : `are`} currently ${nannies} taking care of ${numberWithPlural(V.nurseryChildren, 'child', 'children')}.`,
			maximum: 5,
		};
	}

	/** @returns {FC.IUpgrade[]} */
	get upgrades() {
		return [
			{
				property: "nurseryWeight",
				tiers: [
					{
						value: 0,
						upgraded: 1,
						text: `${this.facility.nameCaps} has only the most basic monitoring systems available.`,
						link: `Upgrade the monitoring system`,
						cost: 1000 * V.upgradeMultiplierArcology,
						handler: () => V.PC.skill.engineering += 0.1,
						note: ` and will increase upkeep costs`,
					},
					{
						value: 1,
						text: `The monitoring systems have been upgraded and allow for monitoring children's food intakes.`,
					},
				],
			},
			{
				property: "nurseryMuscles",
				tiers: [
					{
						value: 0,
						upgraded: 1,
						text: `There is space in one part of ${this.facility.name} where a playground and different toys and equipment could be installed to keep children fit and healthy.`,
						link: `Install a playground`,
						cost: 1000 * V.upgradeMultiplierArcology,
						handler: () => V.PC.skill.engineering += 0.1,
						note: ` and will increase upkeep costs`,
					},
					{
						value: 1,
						text: `A playground and various toys and equipment have been installed in one part of ${this.facility.name}.`,
					},
				],
			},
			{
				property: "nurseryHormones",
				tiers: [
					{
						value: 0,
						upgraded: 1,
						text: `${this.facility.nameCaps} doesn't have any sort of artificial hormones designed for children.`,
						link: `Invest in purpose-built hormones`,
						cost: 1000 * V.upgradeMultiplierArcology,
						handler: () => V.PC.skill.engineering += 0.1,
						note: ` and will increase upkeep costs`,
					},
					{
						value: 1,
						text: `Hormones designed specifically for children have been developed for ${this.facility.name}.`,
					},
				],
			},
		];
	}

	/** @returns {FC.Facilities.Rule[]}*/
	get rules() {
		return [
			{
				property: "MatronIgnoresFlaws",
				prereqs: [
					() => !!S.Matron,
				],
				options: [
					{
						get text() { return `${S.Matron.slaveName} has been instructed to ignore flaws in the nannies serving under ${getPronouns(S.Matron).him}.`; },
						link: `Ignore flaws`,
						value: 1,
					},
					{
						get text() { return `${S.Matron.slaveName} will attempt to fix flaws in nannies serving under ${getPronouns(S.Matron).him}.`; },
						link: `Fix flaws`,
						value: 0,
					},
				],
			},
			{
				property: "nurserySex",
				prereqs: [
					() => !!V.extremeUnderage,
				],
				options: [
					{
						get text() { return `${capFirstChar(V.nurseryName)} staff are not allowed to molest the children.`; },
						link: `Forbid`,
						value: 0,
					},
					{
						get text() { return `${capFirstChar(V.nurseryName)} staff are allowed to molest the children.`; },
						link: `Allow`,
						value: 1,
					},
				],
			},
			// TODO: really not happy with most of these – rework these
			{
				property: "nurseryWeightSetting",
				prereqs: [
					() => !!V.nurseryWeight,
				],
				options: [
					{
						get text() { return `Food intake is not being managed; children may end up malnourished.`; },
						link: `Don't manage`,
						value: 0,
					},
					{
						get text() { return `Food intake is being managed; children will be raised at a healthy weight.`; },
						link: `Manage`,
						value: 1,
					},
				],
			},
			{
				property: "nurseryMusclesSetting",
				prereqs: [
					() => !!V.nurseryMuscles,
				],
				options: [
					{
						get text() { return `Children are not getting any exercise; they may end up quite weak and frail.`; },
						link: `Don't manage`,
						value: 0,
					},
					{
						get text() { return `Exercise is being managed; children will be raised with average fitness.`; },
						link: `Manage`,
						value: 1,
					},
				],
			},
			{
				property: "nurseryHormonesSetting",
				prereqs: [
					() => !!V.nurseryHormones,
				],
				options: [
					{
						get text() { return `Artificial hormones are not being given; children will undergo normal puberty.`; },
						link: `Don't manage`,
						value: 0,
					},
					{
						get text() { return `Artificial hormone levels are being managed; children may experience precocious puberty.`; },
						link: `Manage`,
						value: 1,
					},
				],
			},
		];
	}

	/** @returns {HTMLDivElement} */
	get mothers() {
		const div = document.createElement("div");

		const text = [];

		let childrenReserved = 0;

		text.push(`Reserve an eligible mother-to-be's child to be placed in a room upon birth. Of ${V.nursery} rooms, ${numberWithPlural(V.nursery - V.nurseryChildren, 'is', 'are')} unoccupied. Of those, ${numberWithPlural(FetusGlobalReserveCount("nursery"), 'room is', 'rooms are')} reserved.`);

		App.Events.addNode(div, text);

		const refreshDiv = document.createElement("div");
		refreshDiv.append(content());
		div.append(refreshDiv);

		return div;

		function content() {
			const div = document.createElement("div");

			div.append(
				sort(),
				mothers(),
			);

			return div;
		}

		function sort() {
			const div = document.createElement("div");

			const sorts = [];
			let sort = 'Unsorted';

			sorts.push(App.UI.DOM.link(`Sort by Name`, () => {
				sort = 'Name';
				sortNurseryPossiblesByName();
			}));
			sorts.push(App.UI.DOM.link(`Sort by Reserved Nursery Spots`, () => {
				sort = 'Reserved Nursery Spots';
				sortNurseryPossiblesByReservedSpots();
			}));
			sorts.push(App.UI.DOM.link(`Sort by Pregnancy Week`, () => {
				sort = 'Pregnancy Week';
				sortNurseryPossiblesByPregnancyWeek();
			}));
			sorts.push(App.UI.DOM.link(`Sort by Number of Children`, () => {
				sort = 'Number of Children';
				sortNurseryPossiblesByPregnancyCount();
			}));

			div.append(
				`Sorting: ${sort}`,
				App.UI.DOM.generateLinksStrip(sorts),
			);

			return div;
		}

		function mothers() {
			const el = new DocumentFragment();
			let r = [];
			let eligibility = 0;
			let linkArray;
			const reservedChildren = FetusGlobalReserveCount("incubator");
			const freeRooms = V.nursery - V.nurseryChildren;
			r.push(`Reserve an eligible mother-to-be's child to be placed in a room upon birth. Of ${V.nursery} rooms, ${freeRooms}`);
			if (freeRooms === 1) {
				r.push(`is`);
			} else {
				r.push(`are`);
			}
			r.push(`unoccupied. Of those, ${reservedChildren}`);
			if (reservedChildren === 1) {
				r.push(`room is`);
			} else {
				r.push(`rooms are`);
			}
			r.push(`reserved.`);
			App.Events.addNode(el, r, "div");

			const sortingOptions = new Map([
				["Name", "data-name"],
				["Reserved Incubator Spots", "data-reserved-spots"],
				["Pregnancy Week", "data-preg-week"],
				["Number of Children", "data-preg-count"],
			]);

			if (V.slaves.length > 0) {
			/**
			 * @param {Map<string, string>} sortingOptions
			 */
				const sortingBarFunc = function(sortingOptions) {
					const el = new DocumentFragment();
					App.UI.DOM.appendNewElement("span", el, "Sorting: ", "note");
					const linkArray = [];
					for (const [title, attr] of sortingOptions) {
						if (V.sortIncubatorList === title) {
							linkArray.push(App.UI.DOM.makeElement("span", title, "bold"));
						} else {
							linkArray.push(
								App.UI.DOM.link(
									title,
									() => {
										V.sortIncubatorList = title;
										sortBy(attr);
										jQuery(sortingBar).empty().append(sortingBarFunc(sortingOptions));
									}
								)
							);
						}
					}
					el.append(App.UI.DOM.generateLinksStrip(linkArray));
					return el;
				};

				const sortingBar = document.createElement("div");
				sortingBar.classList.add("incubator-underscore");

				V.sortIncubatorList = V.sortIncubatorList || 'Unsorted';
				sortingBar.append(sortingBarFunc(sortingOptions));
				el.append(sortingBar);
			}

			const qlIncubator = document.createElement("div");
			for (const slave of V.slaves) {
				if (slave.preg > 0 && slave.pregKnown === 1 && slave.eggType === "human") {
					const r = [];
					const reserveDisallowed = (slave.assignment === "work in the dairy" && V.dairyPregSetting > 0) || slave.assignment === "be your agent" || slave.assignment === "live with your agent";
					if (!reserveDisallowed) {
						const {
							His, his
						} = getPronouns(slave);
						const freeRooms = V.nursery - V.nurseryChildren;
						const WL = slave.womb.length;
						const reservedIncubator = WombReserveCount(slave, "incubator");
						const reservedNursery = WombReserveCount(slave, "nursery");
						const momEl = document.createElement("p");
						momEl.id = "slave-" + slave.ID;
						momEl.classList.add("possible");

						momEl.setAttribute("data-preg-count", slave.womb.length.toString());
						momEl.setAttribute("data-reserved-spots", reservedIncubator.toString());
						momEl.setAttribute("data-preg-week", slave.pregWeek.toString());
						momEl.setAttribute("data-name", SlaveFullName(slave));

						linkArray = [];
						const choices = document.createElement("div");
						choices.classList.add("choices");
						r.push(App.UI.DOM.slaveDescriptionDialog(slave));
						r.push(`is ${slave.pregWeek} ${(slave.pregWeek === 1) ? `week` : `weeks`} pregnant with`);
						if (slave.pregSource === 0 || slave.preg <= 5) {
							r.push(`someone's${(slave.preg <= 5) ? `, though it is too early to tell whose,` : ``}`);
						} else if (slave.pregSource === -1) {
							r.push(`your`);
						} else if (slave.pregSource === -2) {
							r.push(`a citizen's`);
						} else if (slave.pregSource === -3) {
							r.push(`your Master's`);
						} else if (slave.pregSource === -4) {
							r.push(`another arcology owner's`);
						} else if (slave.pregSource === -5) {
							r.push(`your client's`);
						} else if (slave.pregSource === -6) {
							r.push(`the Societal Elite's`);
						} else if (slave.pregSource === -7) {
							r.push(`the lab's`);
						} else if (slave.pregSource === -9) {
							r.push(`the Futanari Sisters'`);
						} else {
							const father = getSlave(slave.pregSource);
							if (father) {
								r.push(`${father.slaveName}'s`);
							} else if (WL === 1) {
								r.push("a");
							}
						}
						if (WL > 1) {
							r.push(`${WL} babies.`);
						} else {
							r.push(`baby.`);
						}
						if (reservedIncubator > 0) {
							childrenReserved = 1;
							if (WL === 1) {
								r.push(`${His} child`);
							} else if (reservedIncubator < WL) {
								r.push(`${reservedIncubator} of ${his} children`);
							} else if (WL === 2) {
								r.push(`Both of ${his} children`);
							} else {
								r.push(`All ${reservedIncubator} of ${his} children`);
							}
							r.push(`will be placed in ${V.nurseryName}.`);
							if ((reservedIncubator + reservedNursery < WL) && (reservedChildren < freeRooms)) {
								if (V.pregnancyMonitoringUpgrade === 1) {
									linkArray.push(
										App.UI.DOM.link(
											`Inspect pregnancy`,
											() => {
												V.AS = slave.ID;
											},
											[],
											`Analyze Pregnancy`
										)
									);
								}
								linkArray.push(
									App.UI.DOM.link(
										`Keep another child`,
										() => {
											WombAddToGenericReserve(slave, 'incubator', 1);
											refresh();
										}
									)
								);
								if (reservedIncubator > 0) {
									linkArray.push(
										App.UI.DOM.link(
											`Keep one less child`,
											() => {
												WombCleanGenericReserve(slave, 'incubator', 1);
												refresh();
											}
										)
									);
								}
								if (reservedIncubator > 1) {
									linkArray.push(
										App.UI.DOM.link(
											`Keep none of ${his} children`,
											() => {
												WombCleanGenericReserve(slave, 'incubator', 9999);
												refresh();
											}
										)
									);
								}
								if ((reservedChildren + WL - reservedIncubator) <= freeRooms) {
									linkArray.push(
										App.UI.DOM.link(
											`Keep the rest of ${his} children`,
											() => {
												WombAddToGenericReserve(slave, 'incubator', 9999);
												refresh();
											}
										)
									);
								}
							} else if ((reservedIncubator === WL) || (reservedChildren === freeRooms) || (reservedIncubator + reservedNursery === WL)) {
								if (V.pregnancyMonitoringUpgrade === 1) {
									linkArray.push(
										App.UI.DOM.link(
											`Inspect pregnancy`,
											() => {
												V.AS = slave.ID;
											},
											[],
											`Analyze Pregnancy`
										)
									);
								}
								linkArray.push(
									App.UI.DOM.link(
										`Keep one less child`,
										() => {
											WombCleanGenericReserve(slave, 'incubator', 1);
											refresh();
										}
									)
								);
								if (reservedIncubator > 1) {
									linkArray.push(
										App.UI.DOM.link(
											`Keep none of ${his} children`,
											() => {
												WombCleanGenericReserve(slave, 'incubator', 9999);
												refresh();
											}
										)
									);
								}
							}
						} else if (reservedChildren < freeRooms) {
							if (WL - reservedNursery === 0) {
								r.push(App.UI.DOM.makeElement("span", `${His} children are already reserved for ${V.nurseryName}`, "note"));
								if (V.pregnancyMonitoringUpgrade === 1) {
									linkArray.push(
										App.UI.DOM.link(
											`Inspect pregnancy`,
											() => {
												V.AS = slave.ID;
											},
											[],
											`Analyze Pregnancy`
										)
									);
								}
								linkArray.push(
									App.UI.DOM.link(
										`Keep ${his} ${((WL > 1) ? "children" : "child")} here instead`,
										() => {
											WombChangeReserveType(slave, 'nursery', 'incubator');
											refresh();
										}
									)
								);
							} else {
								r.push(`You have `);
								if (freeRooms === 1) {
									r.push(`an <span class="lime">available aging room.</span>`);
								} else {
									r.push(`<span class="lime">available aging rooms.</span>`);
								}
								if (V.pregnancyMonitoringUpgrade === 1) {
									if (V.pregnancyMonitoringUpgrade === 1) {
										linkArray.push(
											App.UI.DOM.link(
												`Inspect pregnancy`,
												() => {
													V.AS = slave.ID;
												},
												[],
												`Analyze Pregnancy`
											)
										);
									}
								}
								linkArray.push(
									App.UI.DOM.link(
										`Keep ${(WL > 1) ? "a" : "the"} child`,
										() => {
											WombAddToGenericReserve(slave, 'incubator', 1);
											refresh();
										}
									)
								);
								if ((WL > 1) && (reservedChildren + WL - reservedIncubator) <= freeRooms) {
									linkArray.push(
										App.UI.DOM.link(
											`Keep all of ${his} children`,
											() => {
												WombAddToGenericReserve(slave, 'incubator', 9999);
												refresh();
											}
										)
									);
								}
							}
						} else if (reservedChildren === freeRooms) {
							if (V.pregnancyMonitoringUpgrade === 1) {
								linkArray.push(
									App.UI.DOM.link(
										`Inspect pregnancy`,
										() => {
											V.AS = slave.ID;
										},
										[],
										`Analyze Pregnancy`
									)
								);
							}
							const noRoom = new DocumentFragment();
							noRoom.append(`You have `);
							App.UI.DOM.appendNewElement("span", noRoom, `no room for ${his} offspring.`, "red");
							linkArray.push(noRoom);
						}
						eligibility = 1;

						App.Events.addNode(momEl, r, "div");
						choices.append(App.UI.DOM.generateLinksStrip(linkArray));
						momEl.append(choices);
						qlIncubator.append(momEl);
					}
				}
			}
			sortByPreviousSort();
			el.append(qlIncubator);
			if (eligibility === 0) {
				App.UI.DOM.appendNewElement("div", el, `You have no pregnant slaves bearing eligible children.`, "note");
			}

			if (reservedChildren !== 0 || childrenReserved === 1) { // the oops I made it go negative somehow button
				App.UI.DOM.appendNewElement(
					"div",
					el,
					App.UI.DOM.link(
						"Clear all reserved children",
						() => {
							for (const slave of V.slaves) {
								if (WombReserveCount(slave, "incubator") !== 0) {
									WombCleanGenericReserve(slave, 'incubator', 9999);
								}
							}
							WombCleanGenericReserve(V.PC, 'incubator', 9999);
							refresh();
						}
					)
				);
			}
			return el;

			function refresh() {
				App.UI.reload();
			}

			function sortBy(attrName) {
				let sortedIncubatorPossibles = $(qlIncubator).children('p.possible').detach();
				sortedIncubatorPossibles = sortDomObjects(sortedIncubatorPossibles, attrName);
				$(sortedIncubatorPossibles).appendTo(qlIncubator);
			}

			function sortByPreviousSort() {
				const sortAttr = sortingOptions.get(V.sortIncubatorList);
				if (sortAttr) {
					sortBy(sortAttr);
				}
			}
		}
	}

	/** @returns {HTMLDivElement} */
	get children() {
		const div = document.createElement("div");

		div.append(App.Facilities.Nursery.childList());

		return div;
	}

	/** @returns {HTMLDivElement} */
	get targetAge() {
		const div = document.createElement("div");

		const links = [
			App.UI.DOM.link(`Minimum Legal Age`, () => {
				V.targetAgeNursery = V.minimumSlaveAge;

				App.UI.reload();
			}, [], '', `Will not be applied to rooms in use.`),
			App.UI.DOM.link(`Average Age of Fertility`, () => {
				V.targetAgeNursery = V.fertilityAge;

				App.UI.reload();
			}, [], '', `Will not be applied to rooms in use.`),
			App.UI.DOM.link(`Average Age of Potency`, () => {
				V.targetAgeNursery = V.potencyAge;

				App.UI.reload();
			}, [], '', `Will not be applied to rooms in use.`),
			App.UI.DOM.link(`Legal Adulthood`, () => {
				V.targetAgeNursery = 18;

				App.UI.reload();
			}, [], '', `Will not be applied to rooms in use.`),
		];

		div.append(
			`Target age for release: `,
			App.UI.DOM.makeTextBox(V.targetAgeNursery, target => {
				V.targetAgeNursery = target;

				App.UI.reload();
			})
		);

		App.UI.DOM.appendNewElement("div", div, App.UI.DOM.generateLinksStrip(links), ['indent']);

		return div;
	}

	/** @returns {HTMLDivElement} */
	get rooms() {
		const div = document.createElement("div");

		const cost = Math.trunc(5000 * V.upgradeMultiplierArcology);
		const links = [];

		div.append(`It can support ${numberWithPlural(V.nursery, 'child', 'children')}. There ${numberWithPlural(V.nurseryChildren, 'is', 'are')} currently ${numberWithPlural(V.nurseryChildren, 'room')} in use in ${this.facility.name}.`);

		links.push(App.UI.DOM.link(`Add room for another 5 children`, () => {
			cashX(forceNeg(cost), "nursery");
			V.nursery += 5;

			App.UI.reload();
		}, [], '', `Costs ${cashFormat(cost)} and will increase upkeep costs.`));

		if (V.nursery > 1 && FetusGlobalReserveCount("nursery") < V.nursery - V.nurseryChildren) {
			links.push(App.UI.DOM.link(`Remove a room`, () => {
				cashX(forceNeg(cost / 5), "nursery");
				V.nursery -= 5;

				App.UI.reload();
			}, [], '', `Costs ${cashFormat(cost / 5)} and will decrease upkeep costs.`));
		}

		App.UI.DOM.appendNewElement("div", div, App.UI.DOM.generateLinksStrip(links), ['indent']);

		return div;
	}

	/** @returns {HTMLDivElement[]} */
	get customNodes() {
		return [
			this.mothers,
			this.children,
			this.targetAge,
			this.rooms,
		];
	}
};


code:
App.Facilities.Nursery.ChildDatatypeCleanup = function(child) {
	childAgeDatatypeCleanup(child);
	childPhysicalDatatypeCleanup(child);
	childFaceDatatypeCleanup(child);
	childHairDatatypeCleanup(child);
	childBoobsDatatypeCleanup(child);
	childButtDatatypeCleanup(child);
	childPregnancyDatatypeCleanup(child);
	childBellyDatatypeCleanup(child);
	childGenitaliaDatatypeCleanup(child);
	childImplantsDatatypeCleanup(child);
	childPiercingsDatatypeCleanup(child);
	childTattooDatatypeCleanup(child);
	childCosmeticsDatatypeCleanup(child);
	childDietDatatypeCleanup(child);
	childPornDatatypeCleanup(child);
	childRelationDatatypeCleanup(child);
	childSkillsDatatypeCleanup(child);
	childStatCountDatatypeCleanup(child);
	childPreferencesDatatypeCleanup(child);
	childRulesDatatypeCleanup(child);
	childCustomStatsDatatypeCleanup(child);
	childMiscellaneousDatatypeCleanup(child);
	generatePronouns(child);

	function childAgeDatatypeCleanup(child) {
		child.birthWeek = Math.clamp(+child.birthWeek, 0, 51) || 0;
		if (child.age > 0) {
			child.actualAge = Math.clamp(+child.actualAge, 0, Infinity) || child.age; /* if undefined, this sets to child.age */
			delete child.age;
		} else {
			child.actualAge = Math.clamp(+child.actualAge, 0, Infinity) || 3;
		}
		child.visualAge = Math.max(+child.visualAge, 0) || child.actualAge;
		child.physicalAge = Math.max(+child.physicalAge, 0) || child.actualAge;
		child.ovaryAge = Math.max(+child.ovaryAge, 0) || child.physicalAge;
		child.pubertyAgeXX = Math.max(+child.pubertyAgeXX, 0) || V.fertilityAge;
		child.pubertyAgeXY = Math.max(+child.pubertyAgeXY, 0) || V.potencyAge;
	}

	function childPhysicalDatatypeCleanup(child) {
		if (typeof child.nationality !== "string" || child.nationality === "child") {
			child.nationality = "slave";
		}
		if (typeof child.race !== "string") {
			nationalityToRace(child);
		}
		if (typeof child.origRace !== "string") {
			child.origRace = child.race;
		}
		if (typeof child.skin !== "string") {
			child.skin = "light";
		}
		if (typeof child.origSkin !== "string") {
			child.origSkin = child.skin;
		}
		if (typeof child.minorInjury !== "string") {
			child.minorInjury = 0;
		}
		if (typeof child.health === "number") {
			const condition = child.health;
			child.health = {};
			child.health.condition = condition;
		}
		child.health.condition = Math.clamp(+child.health.condition, -100, 100) || 0;
		child.health.shortDamage = Math.max(+child.health.shortDamage, 0) || 0;
		child.health.longDamage = Math.max(+child.health.longDamage, 0) || 0;
		child.health.illness = Math.max(+child.health.illness, 0) || 0;
		child.health.tired = Math.clamp(+child.health.tired, 0, 100) || 0;
		child.muscles = Math.clamp(+child.muscles, -100, 100) || 0;
		child.weight = Math.clamp(+child.weight, -100, 200) || 0;
		child.waist = Math.clamp(+child.waist, -100, 100) || 0;
		child.height = Math.round(Math.max(+child.height, 0)) || Height.mean(child);
		child.shoulders = Math.clamp(+child.shoulders, -2, 2) || 0;
		child.hips = Math.clamp(+child.hips, -2, 3) || 0;
	}

	function childFaceDatatypeCleanup(child) {
		child.face = Math.clamp(+child.face, -100, 100) || 0;
		if (typeof child.faceShape !== "string") {
			child.faceShape = "normal";
		}
		if (child.lips !== 0) {
			child.lips = Math.clamp(+child.lips, 0, 100) || 15;
		}
	}

	function childHairDatatypeCleanup(child) {
		if (typeof child.hColor !== "string") {
			child.hColor = "brown";
		}
		if (typeof child.origHColor !== "string") {
			child.origHColor = child.hColor;
		}
		if (child.hLength !== 0) {
			child.hLength = Math.clamp(+child.hLength, 0, 300) || 60;
		}
		if (typeof child.hStyle !== "string") {
			child.hStyle = "long";
		}
		child.haircuts = Math.clamp(+child.haircuts, 0, 1) || 0;
		child.bald = Math.clamp(+child.bald, 0, 1) || 0;
		if (typeof child.pubicHColor !== "string") {
			child.pubicHColor = child.hColor;
		}
		if (typeof child.pubicHStyle !== "string") {
			child.pubicHStyle = "neat";
		}
		if (typeof child.underArmHColor !== "string") {
			child.underArmHColor = child.hColor;
		}
		if (typeof child.underArmHStyle !== "string") {
			child.underArmHStyle = "waxed";
		}
		if (typeof child.eyebrowHColor !== "string") {
			child.eyebrowHColor = child.hColor;
		}
		if (typeof child.eyebrowHStyle !== "string") {
			child.eyebrowHStyle = "natural";
		}
		if (typeof child.eyebrowFullness !== "string") {
			child.eyebrowFullness = "natural";
		}
	}

	function childBoobsDatatypeCleanup(child) {
		child.boobs = Math.max(+child.boobs, 100) || 200;
		if (typeof child.boobShape !== "string") {
			child.boobShape = "normal";
		}
		if (typeof child.nipples !== "string") {
			child.nipples = "cute";
		}
		if (typeof child.nipplesAccessory !== "string") {
			child.nipplesAccessory = "none";
		}
		child.areolae = Math.clamp(+child.areolae, 0, 4) || 0;
		if (typeof child.areolaeShape !== "string") {
			child.areolaeShape = "circle";
		}
		child.lactation = Math.clamp(+child.lactation, 0, 2) || 0;
		child.lactationAdaptation = Math.clamp(+child.lactationAdaptation, 0, 100) || 0;
	}

	function childButtDatatypeCleanup(child) {
		if (child.butt !== 0) {
			child.butt = Math.clamp(+child.butt, 0, 20) || 1;
		}
		child.anus = Math.clamp(+child.anus, 0, 4) || 0;
		child.analArea = Math.max(+child.analArea, 0) || 0;
	}

	function childPregnancyDatatypeCleanup(child) {
		child.induce = Math.clamp(+child.induce, 0, 1) || 0;
		child.labor = Math.clamp(+child.labor, 0, 1) || 0;
		if (child.hasOwnProperty("cSec")) {
			if (child.cSec > 0) {
				App.Medicine.Modification.addScar(child, "belly", "c-section");
			}
			delete child.cSec;
		}
		child.prematureBirth = Math.clamp(+child.prematureBirth, 0, 1) || 0;
		child.ovaries = Math.clamp(+child.ovaries, 0, 1) || 0;
		child.vasectomy = Math.clamp(+child.vasectomy, 0, 1) || 0;
		child.mpreg = Math.clamp(+child.mpreg, 0, 1) || 0;
		if (child.pregAdaptation !== 0) {
			child.pregAdaptation = Math.max(+child.pregAdaptation, 0) || 50;
		}
		child.pregSource = +child.pregSource || 0;
		if (typeof child.pregControl !== "string") {
			child.pregControl = "none";
		}
		child.fertPeak = Math.clamp(+child.fertPeak, 0, 4) || 0;
		WombNormalizePreg(child);
	}

	function childBellyDatatypeCleanup(child) {
		child.bellySag = Math.max(+child.bellySag, 0) || 0;
		child.bellySagPreg = Math.max(+child.bellySagPreg, 0) || child.bellySag;
		SetBellySize(child);
	}

	function childGenitaliaDatatypeCleanup(child) {
		child.vagina = Math.clamp(+child.vagina, -1, 10) || 0;
		child.vaginaLube = Math.clamp(+child.vaginaLube, 0, 2) || 0;
		child.labia = Math.clamp(+child.labia, 0, 3) || 0;
		child.clit = Math.clamp(+child.clit, 0, 5) || 0;
		child.foreskin = Math.max(+child.foreskin, 0) || 0;
		child.dick = Math.max(+child.dick, 0) || 0;
		if (child.dick && child.prostate !== 0) {
			child.prostate = Math.clamp(+child.prostate, 0, 3) || 1;
		} else {
			child.prostate = Math.clamp(+child.prostate, 0, 3) || 0;
		}
		child.balls = Math.max(+child.balls, 0) || 0;
		if (child.scrotum !== 0) {
			child.scrotum = Math.max(+child.scrotum, 0) || child.balls;
		}
	}

	function childImplantsDatatypeCleanup(child) {
		child.ageImplant = Math.clamp(+child.ageImplant, 0, 1) || 0;
		child.faceImplant = Math.clamp(+child.faceImplant, 0, 100) || 0;
		child.lipsImplant = Math.clamp(+child.lipsImplant, 0, 100) || 0;
		child.voiceImplant = Math.clamp(+child.voiceImplant, -1, 1) || 0;
		child.boobsImplant = Math.max(+child.boobsImplant, 0) || 0;
		if (child.boobsImplant === 0) {
			child.boobsImplantType = "none";
		} else if (child.boobsImplantType === "none") {
			child.boobsImplantType = "normal";
		}
		child.breastMesh = Math.clamp(+child.breastMesh, 0, 1) || 0;
		child.buttImplant = Math.clamp(+child.buttImplant, 0, 3) || 0;
		if (child.buttImplant === 0) {
			child.buttImplantType = "none";
		} else if (child.buttImplantType === "none") {
			child.buttImplantType = "normal";
		}
		child.earImplant = Math.clamp(+child.earImplant, 0, 1) || 0;
	}

	function childPiercingsDatatypeCleanup(child) {
		child.piercing = child.piercing || {}; //areolae and nipples
		const oldPiercings = new Map([
			["nipple", "nipples"],
			["areola", "areolae"],
		]);
		for (const piercing of Object.keys(App.Data.Piercings)) {
			child.piercing[piercing] = child.piercing[piercing] || new App.Entity.piercingState();
			const oldPiercing = `${oldPiercings.get(piercing) || piercing}Piercing`; // the old variable names were sometimes plural and sometimes singular. The new standard is to use singular when possible.
			if (child.hasOwnProperty(oldPiercing)) {
				if (child[oldPiercing] === 3) { // 3 used to indicate a smart piercing. We now track this on a separate property as a bool.
					child.piercing[piercing].weight = 2;
					child.piercing[piercing].smart = true;
				} else if (child[oldPiercing]) {
					child.piercing[piercing].weight = child[oldPiercing];
				}
				delete child[oldPiercing];
			}
		}
	}

	function childTattooDatatypeCleanup(child) {
		if (typeof child.shouldersTat !== "string") {
			child.shouldersTat = 0;
		}
		if (typeof child.lipsTat !== "string") {
			child.lipsTat = 0;
		}
		if (typeof child.boobsTat !== "string") {
			child.boobsTat = 0;
		}
		if (typeof child.armsTat !== "string") {
			child.armsTat = 0;
		}
		if (typeof child.backTat !== "string") {
			child.backTat = 0;
		}
		if (typeof child.stampTat !== "string") {
			child.stampTat = 0;
		}
		if (typeof child.buttTat !== "string") {
			child.buttTat = 0;
		}
		if (typeof child.vaginaTat !== "string") {
			child.vaginaTat = 0;
		}
		if (typeof child.dickTat !== "string") {
			child.dickTat = 0;
		}
		if (typeof child.anusTat !== "string") {
			child.anusTat = 0;
		}
		if (typeof child.legsTat !== "string") {
			child.legsTat = 0;
		}
		if (typeof child.bellyTat !== "string") {
			child.bellyTat = 0;
		}
		if (typeof child.custom.tattoo !== "string") {
			child.custom.tattoo = "";
		}
	}

	function childCosmeticsDatatypeCleanup(child) {
		child.makeup = Math.clamp(+child.makeup, 0, 8) || 0;
		child.nails = Math.clamp(+child.nails, 0, 9) || 0;
		child.scars = Math.clamp(+child.scars, 0, 6) || 0;
		child.chastityAnus = Math.clamp(+child.chastityAnus, 0, 1) || 0;
		child.chastityPenis = Math.clamp(+child.chastityPenis, 0, 1) || 0;
		child.chastityVagina = Math.clamp(+child.chastityVagina, 0, 1) || 0;
		child.choosesOwnClothes = Math.clamp(+child.choosesOwnClothes, 0, 1) || 0;
		if (typeof child.clothes !== "string") {
			child.clothes = "no clothing";
		}
		if (typeof child.collar !== "string") {
			child.collar = "none";
		}
		if (typeof child.shoes !== "string") {
			child.shoes = "none";
		}
		if (typeof child.eyewear !== "string") {
			child.eyewear = "none";
		}
		if (typeof child.brand !== "object") {
			let brand = {};
			if (child.brand !== 0) {
				brand["left buttock"] = child.brand;
			}
			child.brand = brand;
		} else if (typeof child.brand === "object") { // Make sure key and value are strings
			for (let [key, value] of Object.entries(child.brand)) {
				if (typeof key !== "string" || typeof value !== "string") {
					delete child.brand[key];
				}
			}
		}
		if (typeof child.markings !== "string") {
			child.markings = "none";
		}
		if (typeof child.bellyAccessory !== "string") {
			child.bellyAccessory = "none";
		}
		if (typeof child.vaginalAccessory !== "string") {
			child.vaginalAccessory = "none";
		}
		if (typeof child.vaginalAttachment !== "string") {
			child.vaginalAttachment = "none";
		}
		if (typeof child.dickAccessory !== "string") {
			child.dickAccessory = "none";
		}
		if (typeof child.legAccessory !== "string") {
			child.legAccessory = "none";
		}
		if (typeof child.buttplug !== "string") {
			child.buttplug = "none";
		}
		if (typeof child.buttplugAttachment !== "string") {
			child.buttplugAttachment = "none";
		}
		if (typeof child.faceAccessory !== "string") {
			child.faceAccessory = "none";
		}
		if (typeof child.mouthAccessory !== "string") {
			child.mouthAccessory = "none";
		}
		switch(child.collar) {
			case "porcelain mask":
				child.faceAccessory = child.collar;
				child.collar = "none";
				break;
			case "bit gag":
			case "dildo gag":
			case "massive dildo gag":
			case "ball gag":
			case "ring gag":
				child.mouthAccessory = child.collar;
				child.collar = "none";
				break;
		}
	}

	function childDietDatatypeCleanup(child) {
		if (typeof child.diet !== "string") {
			child.diet = "healthy";
		}
		child.dietCum = Math.clamp(+child.dietCum, 0, 2) || 0;
		child.dietMilk = Math.clamp(+child.dietMilk, 0, 2) || 0;
		child.onDiet = Math.clamp(+child.onDiet, 0, 1) || 0;
		child.hormones = Math.clamp(+child.hormones, -2, 2) || 0;
		child.hormoneBalance = Math.clamp(+child.hormoneBalance, -400, 400) || 0;
		if (typeof child.drugs !== "string") {
			child.drugs = "no drugs";
		}
		child.aphrodisiacs = Math.clamp(+child.aphrodisiacs, 0, 2) || 0;
		child.curatives = Math.clamp(+child.curatives, 0, 2) || 0;
	}

	function childPornDatatypeCleanup(child) {
		child.porn.feed = Math.clamp(+child.porn.feed, 0, 1) || 0;
		child.porn.viewerCount = Math.max(+child.porn.viewerCount, 0) || 0;
		child.porn.spending = Math.max(+child.porn.spending, 0) || 0;
		child.porn.prestige = Math.clamp(+child.porn.prestige, 0, 3) || 0;
		if (typeof child.porn.prestigeDesc !== "string") {
			child.porn.prestigeDesc = 0;
		}
		if (typeof child.porn.fameType !== "string") {
			child.porn.fameType = "none";
		}
		if (typeof child.porn.focus !== "string") {
			child.porn.focus = "none";
		}
		for (const genre of App.Porn.getAllGenres()) {
			child.porn.fame[genre.fameVar] = Math.max(+child.porn.fame[genre.fameVar], 0) || 0;
		}
	}

	function childRelationDatatypeCleanup(child) {
		child.mother = +child.mother || 0;
		child.father = +child.father || 0;
		child.canRecruit = Math.clamp(+child.canRecruit, 0, 1) || 0;
		child.relationship = Math.clamp(+child.relationship, -3, 5) || 0;
		child.relationshipTarget = Math.max(+child.relationshipTarget, 0) || 0;
		child.rivalryTarget = Math.max(+child.rivalryTarget, 0) || 0;
		child.rivalry = Math.clamp(+child.rivalry, 0, 3) || 0;
	}

	function childSkillsDatatypeCleanup(child) {
		child.skill.oral = Math.clamp(+child.skill.oral, 0, 100) || 0;
		child.skill.vaginal = Math.clamp(+child.skill.vaginal, 0, 100) || 0;
		child.skill.anal = Math.clamp(+child.skill.anal, 0, 100) || 0;
		child.skill.whoring = Math.clamp(+child.skill.whoring, 0, 100) || 0;
		child.skill.entertainment = Math.clamp(+child.skill.entertainment, 0, 100) || 0;
		child.skill.combat = Math.clamp(+child.skill.combat, 0, 1) || 0;
		child.skill.headGirl = Math.clamp(+child.skill.headGirl, 0, 200) || 0;
		child.skill.recruiter = Math.clamp(+child.skill.recruiter, 0, 200) || 0;
		child.skill.bodyguard = Math.clamp(+child.skill.bodyguard, 0, 200) || 0;
		child.skill.madam = Math.clamp(+child.skill.madam, 0, 200) || 0;
		child.skill.DJ = Math.clamp(+child.skill.DJ, 0, 200) || 0;
		child.skill.nurse = Math.clamp(+child.skill.nurse, 0, 200) || 0;
		child.skill.teacher = Math.clamp(+child.skill.teacher, 0, 200) || 0;
		child.skill.attendant = Math.clamp(+child.skill.attendant, 0, 200) || 0;
		child.skill.matron = Math.clamp(+child.skill.matron, 0, 200) || 0;
		child.skill.stewardess = Math.clamp(+child.skill.stewardess, 0, 200) || 0;
		child.skill.milkmaid = Math.clamp(+child.skill.milkmaid, 0, 200) || 0;
		child.skill.farmer = Math.clamp(+child.skill.farmer, 0, 200) || 0;
		child.skill.wardeness = Math.clamp(+child.skill.wardeness, 0, 200) || 0;
		child.skill.servant = Math.clamp(+child.skill.servant, 0, 200) || 0;
		child.skill.entertainer = Math.clamp(+child.skill.entertainer, 0, 200) || 0;
		child.skill.whore = Math.clamp(+child.skill.whore, 0, 200) || 0;
	}

	function childStatCountDatatypeCleanup(child) {
		child.counter.oral = Math.max(+child.counter.oral, 0) || 0;
		child.counter.vaginal = Math.max(+child.counter.vaginal, 0) || 0;
		child.counter.anal = Math.max(+child.counter.anal, 0) || 0;
		child.counter.publicUse = Math.max(+child.counter.publicUse, 0) || 0;
		child.counter.mammary = Math.max(+child.counter.mammary, 0) || 0;
		child.counter.penetrative = Math.max(+child.counter.penetrative, 0) || 0;
		child.counter.pitKills = Math.max(+child.counter.pitKills, 0) || 0;
		child.counter.milk = Math.max(+child.counter.milk, 0) || 0;
		child.counter.cum = Math.max(+child.counter.cum, 0) || 0;
		child.counter.births = Math.max(+child.counter.births, 0) || 0;
		child.counter.birthsTotal = Math.max(+child.counter.birthsTotal, 0) || child.counter.births;
		child.counter.laborCount = Math.max(+child.counter.laborCount, 0) || child.counter.birthsTotal;
		child.counter.PCChildrenFathered = Math.max(+child.counter.PCChildrenFathered, 0) || 0;
		child.counter.PCKnockedUp = Math.max(+child.counter.PCKnockedUp, 0) || 0;
		child.bodySwap = Math.max(+child.bodySwap, 0) || 0;
	}

	function childPreferencesDatatypeCleanup(child) {
		child.energy = Math.clamp(+child.energy, 0, 100) || 0;
		child.need = Math.max(+child.need, 0) || 0;
		child.attrXY = Math.clamp(+child.attrXY, 0, 100) || 0;
		child.attrXX = Math.clamp(+child.attrXX, 0, 100) || 0;
		child.attrKnown = Math.clamp(+child.attrKnown, 0, 1) || 0;
		child.fetishStrength = Math.clamp(+child.fetishStrength, 0, 100) || 0;
		child.fetishKnown = Math.clamp(+child.fetishKnown, 0, 1) || 0;
	}

	function childRulesDatatypeCleanup(child) {
		child.breedingMark = Math.clamp(+child.breedingMark, 0, 1) || 0;
		child.rudeTitle = Math.clamp(+child.rudeTitle, 0, 1) || 0;
	}

	function childCustomStatsDatatypeCleanup(child) {
		if (typeof child.custom.label !== "string") {
			child.custom.label = "";
		}
		if (typeof child.custom.desc !== "string") {
			child.custom.desc = "";
		}
		if (typeof child.custom.title !== "string") {
			child.custom.title = "";
		}
		if (typeof child.custom.titleLisp !== "string") {
			child.custom.titleLisp = "";
		}
		if (child.custom.image !== null) {
			if (typeof child.custom.image.filename !== "string") {
				child.custom.image = null;
			}
		}
	}

	function childMiscellaneousDatatypeCleanup(child) {
		child.weekAcquired = Math.max(+child.weekAcquired, 0) || 0;
		child.prestige = Math.clamp(+child.prestige, 0, 3) || 0;
		child.devotion = Math.clamp(+child.devotion, -100, 100) || 0;
		child.oldDevotion = Math.clamp(+child.oldDevotion, -100, 100) || 0;
		child.trust = Math.clamp(+child.trust, -100, 100) || 0;
		child.oldTrust = Math.clamp(+child.oldTrust, -100, 100) || 0;
		child.chem = Math.max(+child.chem, 0) || 0;
		child.addict = Math.max(+child.addict, 0) || 0;
		child.intelligence = Math.clamp(+child.intelligence, -100, 100) || 0;
		child.intelligenceImplant = Math.clamp(+child.intelligenceImplant, 0, 30) || 0;
		child.premature = Math.clamp(+child.premature, 0, 1) || 0;
		child.training = Math.clamp(+child.training, 0, 150) || 0;
		child.hears = Math.clamp(+child.hears, -2, 0) || 0;
		child.smells = Math.clamp(+child.smells, -1, 0) || 0;
		child.tastes = Math.clamp(+child.tastes, -1, 0) || 0;
		if (typeof child.earwear !== "string") {
			child.earwear = "none";
		}
		if (child.voice !== 0) {
			child.voice = Math.clamp(+child.voice, 0, 3) || 1;
		}
		child.electrolarynx = Math.clamp(+child.electrolarynx, 0, 1) || 0;
		child.accent = Math.clamp(+child.accent, 0, 3) || 0;
	}
};

App.Facilities.Nursery.InfantDatatypeCleanup = function(child) {
	"use strict";

	ageDatatypeCleanup(child);
	physicalDatatypeCleanup(child);
	faceDatatypeCleanup(child);
	hairDatatypeCleanup(child);
	relationDatatypeCleanup(child);
	originDatatypeCleanup(child);
	generatePronouns(child);

	child.premature = Math.clamp(+child.premature, 0, 1) || 0;
	child.addict = Math.max(+child.addict, 0) || 0;

	// old versions of FC assign overlapping IDs to infants and other slaves, which needs to be fixed
	// deconflict IDs between infants and older children/tank babies/adults by reassigning the infant's ID
	if (V.cribs.find((s) => s.ID === child.ID && (s.birthWeek !== child.birthWeek || s.actualAge !== child.actualAge)) !== undefined
	 || V.slaves.find((s) => s.ID === child.ID) !== undefined || (V.incubator.tanks.find((s) => s.ID === child.ID) !== undefined)) {
		child.ID = generateSlaveID();
	}

	function ageDatatypeCleanup(child) {
		child.birthWeek = Math.clamp(+child.birthWeek, 0, 51) || 0;
		child.actualAge = Math.clamp(+child.actualAge, 0, Infinity) || 0;
	}

	function physicalDatatypeCleanup(child) {
		if (typeof child.nationality !== "string" || child.nationality === "child") {
			child.nationality = "slave";
		}
		if (typeof child.race !== "string") {
			nationalityToRace(child);
		}
		if (typeof child.skin !== "string") {
			child.skin = "light";
		}
		child.weight = Math.clamp(+child.weight, -100, 200) || 0;
	}

	function faceDatatypeCleanup(child) {
		child.face = Math.clamp(+child.face, -100, 100) || 0;
		if (typeof child.faceShape !== "string") {
			child.faceShape = "normal";
		}
	}

	function hairDatatypeCleanup(child) {
		if (typeof child.hColor !== "string") {
			child.hColor = "brown";
		}
		if (typeof child.pubicHStyle !== "string") {
			child.pubicHStyle = "neat";
		}
		if (typeof child.eyebrowHColor !== "string") {
			child.eyebrowHColor = child.hColor;
		}
	}

	function relationDatatypeCleanup(child) {
		child.mother = +child.mother || 0;
		child.father = +child.father || 0;
		child.cloneID = +child.cloneID || 0;
	}

	function originDatatypeCleanup(child) {
		if (typeof child.origin !== "string") {
			child.origin = `${capFirstChar(child.pronoun)} was born and raised in your arcology. `;
		}
	}
};


code:
:: Nursery Discard Workaround [nobr]

$activeSlave.slaveName has been given away to another arcology to be raised, never to be seen again.

<<set $returnTo = "Main">>


code:
App.Data.Facilities.nursery = {
	baseName: "nursery",
	genericName: null,
	jobs: {
		nanny: {
			position: "nanny",
			assignment: Job.NURSERY,
			publicSexUse: false,
			fuckdollAccepted: false
		}
	},
	defaultJob: "nanny",
	manager: {
		position: "matron",
		assignment: Job.MATRON,
		careers: App.Data.Careers.Leader.matron,
		skill: "matron",
		publicSexUse: false,
		fuckdollAccepted: false,
		broodmotherAccepted: false,
		shouldWalk: true,
		shouldHold: true,
		shouldSee: true,
		shouldHear: true,
		shouldTalk: true,
		shouldThink: true,
		requiredDevotion: 51
	},
	decorated: true
};

App.Entity.Facilities.NurseryNannyJob = class extends App.Entity.Facilities.FacilitySingleJob {
	/**
	 * @param {App.Entity.SlaveState} slave
	 * @returns {string[]}
	 */
	checkRequirements(slave) {
		let r = super.checkRequirements(slave);

		if (!App.Entity.Facilities.Job._isBrokenEnough(slave, 51, 21, -20, -95)) {
			r.push(App.Entity.Facilities.Job._stdBreakageMessage(slave));
		}

		return r;
	}

	/**
	 * @override
	 */
	get assignment() {
		return `work in ${this.facility.name}`;
	}
};

App.Entity.Facilities.Nursery = class extends App.Entity.Facilities.SingleJobFacility {
	constructor() {
		super(App.Data.Facilities.nursery,
			{
				nanny: new App.Entity.Facilities.NurseryNannyJob()
			});
	}

	// get capacity() {
	// 	return State.Variables.nurseryNannies;
	// }

	/** @override */
	occupancyReport(long) {
		return long
			? `${V.nurseryChildren}/${V.nursery} babies, ${this.hostedSlaves}/${V.nurseryNannies} nannies${this.manager.currentEmployee ? `, ${this.manager.desc.position}` : ""}`
			: `${V.nurseryChildren}/${V.nursery}, ${this.hostedSlaves}/${V.nurseryNannies}${this.manager.currentEmployee ? ", L" : ""}`;
	}
};

App.Entity.facilities.nursery = new App.Entity.Facilities.Nursery();


code:
:: Previous Child In Line

<<silently>>

<<set $i = $cribs.findIndex(function(c) { return c.ID === $activeChild.ID; })>>
<<set $cribs[$i] = $activeChild>> /* save changes before switching */
<<if $i == 0>>
	<<set $activeChild = $cribs[$cribs.length - 1]>>
	<<if $activeChild.actualAge < 3>>
		<<goto "Infant Interact">>
	<<else>>
		<<goto "Child Interact">>
	<</if>>
<<else>>
	<<set $activeChild = $cribs[$i-1]>>
	<<if $activeChild.actualAge < 3>>
		<<goto "Infant Interact">>
	<<else>>
		<<goto "Child Interact">>
	<</if>>
<</if>>

<</silently>>


code:
App.Facilities.Nursery.fChildOral = function fChildOral(child) {
	"use strict";

	let r = ``;

	actX(child, "oral");// TODO: will this counts towards the total count?

	// TODO: all of this

	return r;
};

App.Facilities.Nursery.fChildVaginal = function fChildVaginal(child) {
	"use strict";

	let r = ``;

	actX(child, "vaginal");// TODO: will this counts towards the total count?

	// TODO: all of this

	return r;
};

App.Facilities.Nursery.fChildAnal = function fChildAnal(child) {
	"use strict";

	let r = ``;

	actX(child, "anal");

	// TODO: all of this

	return r;
};

App.Facilities.Nursery.fChildImpreg = function fChildImpreg(child) {
	const bonus = jsRandom(6, 20);

	let r = ``;

	if (child.mpreg) {
		actX(child, "anal", (bonus + 1));
	} else {
		actX(child, "vaginal", (bonus + 1));
	}

	// TODO: all of this

	return r;
};