code:
package classes.Scenes.Quests.UrtaQuest
{
	import classes.*;
	import classes.GlobalFlags.kGAMECLASS;
	import classes.Scenes.Monsters.AbstractSuccubus;
	import classes.internals.*;

	use namespace kGAMECLASS;

	public class MilkySuccubus extends AbstractSuccubus
	{

		override protected function performCombatAction():void
		{
			if (findStatusEffect(StatusEffects.MilkyUrta) < 0 && rand(3) == 0) cowCubiMilkSprayAttack();
			else if (HP < 400) drinkMinoCum();
			else if (player.HP < 100) eAttack();
			else if (player.lust >= 90) succubusTease();
			else if (rand(2) == 0) succubusTease();
			else eAttack();
		}

		private function cowCubiMilkSprayAttack():void
		{
			//Lasts a couple turns like the goblin lust poison?
			outputText("\"How about a taste?\"  The succubus asks, pressing her tits together.  Before you can reply, a veritable jet of milk sprays in your direction!\n");
//Miss:
			if (rand(20) + 1 + player.spe / 20 > 17) {
				outputText("With your trained reflexes, you manage to duck and roll, narrowly avoiding getting sprayed with milk.");
				outputText("\n\n\"Such a waste.\"  The succubus pouts.  \"No worries, I'll just have Fido clean it up later... perhaps I'll even have you do it later, when you become mine.\"  The succubus giggles.");
				kGAMECLASS.dynStats("lus", 6);
			}
			//Hit:
			else {
				outputText("All you manage to do is cover your face; the rest of you, however, gets completely soaked in the demon's corrupted milk.  Looking down at yourself, you realize that you are panting, and the places where the milk splashed your fur begin to heat up.  Oh no! You'd better finish off this succubus before you succumb to your lusts!");
				kGAMECLASS.dynStats("lus", 15);
				createStatusEffect(StatusEffects.MilkyUrta, 3, 0, 0, 0);
			}
			combatRoundOver();
		}

		private function drinkMinoCum():void
		{
			outputText("Smiling wryly and licking her lips, the succubus-cow procures a bottle of her pet's cum with her probing tail.");
//Success:
			if (findStatusEffect(StatusEffects.DrankMinoCum) < 0 || findStatusEffect(StatusEffects.DrankMinoCum2) < 0) {
				outputText("\n\nSmiling triumphantly, she takes the bottle and opens it with a pop, drinking the contents with glee.  When done, she throws the bottle away and smacks her lips.  \"Nothing like a bottle of minotaur cum to get you back on your feet, right?\"  She grins, her pussy dripping with more juices.");
				addHP(400);
				lust += 25;
				if (findStatusEffect(StatusEffects.DrankMinoCum) < 0) createStatusEffect(StatusEffects.DrankMinoCum, 0, 0, 0, 0);
				else createStatusEffect(StatusEffects.DrankMinoCum2, 0, 0, 0, 0);
			}
			//Failure:
			else {
				outputText("\n\nShe frowns and looks behind her, pouting slightly when she turns to look back at you.  \"Seems like I'm all out of cum.\"  She grins evilly.  \"I'll just have to get more after I'm done with you.\"");
			}
			combatRoundOver();
		}

		private function succubusTease():void
		{
			if (rand(4) == 0) outputText("Turning around, the succubus begins to bounce her rather round derriere in your direction, the cheeks lewdly clapping together with each change in direction, exposing her dark anal star and juicy snatch, literally gushing forth a stream of lubricants.  Her eyes glow with faint, purple light as she whispers, \"Don't you just want to... slide on in?\"");
			else if (rand(3) == 0) outputText("The succubus squeezes her spotted, sweat-oiled breasts together, squirting out trickles of fresh, creamy, succubi milk.  Bending down, she laps at her own bounty, taking to meet your eyes, her own glowing violet.  You can feel her next words as much as hear them, reaching into your brain and stirring a familiar heat in your loins.  \"Giving in would mean pleasure unending, my dear vixen.\"");
			else if (rand(2) == 0) outputText("The succubus turns slightly and slowly bends over, sliding her hands down the sides of her milk laden jugs. \"Mmm, would you help a poor girl relax? These things need some attention,\" she says with a lust filled moan as her hands reach her multitude of nipples.");
			else outputText("The succubus leans forwards holding her tits, while wrapping her fingers around her nipples.  \"My boobs are soo full.  Would you like to help me drain them?\" she says with a husky voice.");
			kGAMECLASS.dynStats("lus", 20);
			combatRoundOver();
		}

		override public function defeated(hpVictory:Boolean):void
		{
			game.urtaQuest.urtaBeatsUpCowcubi();
		}

		override public function won(hpVictory:Boolean, pcCameWorms:Boolean):void
		{
			game.urtaQuest.urtaLosesToCowCubi();
		}

		override public function teased(lustDelta:Number):void
		{
			outputText(capitalA + short + " smiles, rubbing her hands across herself as she watches your display.  She does not seem greatly affected by your show - at least in the sense of increasing arousal.  She does seem oddly more... vital, as if she drew strength from the very display you put on.");
			str += 5;
			addHP(50);
			applyTease(lustDelta);
		}

		public function MilkySuccubus()
		{
			this.a = "the ";
			this.short = "milky succubus";
			this.imageName = "milkysuccubus";
			this.long = "You are fighting a milky, cow-like succubus.  She stands about seven feet tall and is hugely voluptuous, with breasts three times the size of her head, tipped with a cluster of four obscenely teat-like nipples.  Her hips flare out into an exaggerated hourglass shape, with a long tail tipped with a fleshy arrow-head spade that waves above her spankable butt.  A small cowbell is tied at the base of the arrow-head with a cute little ribbon.  Wide, cow-like horns, easily appropriate for a minotaur, rise from her head, and she flicks bovine ears about the sides of her head whilst sashaying from side to side on demonic, high-heeled feet.  Her skin is a vibrant purple with splotches of shiny black here and there, including one large spot covering her right eye.  She's using a leather whip as a weapon.";
			// this.plural = false;
			this.createVagina(false, VAGINA_WETNESS_SLAVERING, VAGINA_LOOSENESS_NORMAL);
			this.createStatusEffect(StatusEffects.BonusVCapacity, 300, 0, 0, 0);
			createBreastRow(Appearance.breastCupInverse("G"));
			this.ass.analLooseness = ANAL_LOOSENESS_STRETCHED;
			this.ass.analWetness = ANAL_WETNESS_SLIME_DROOLING;
			this.tallness = 84;
			this.hipRating = HIP_RATING_CURVY;
			this.buttRating = BUTT_RATING_LARGE+1;
			this.lowerBody = LOWER_BODY_TYPE_DEMONIC_HIGH_HEELS;
			this.skinTone = "blue";
			this.hairColor = "black";
			this.hairLength = 13;
			initStrTouSpeInte(75, 50, 125, 95);
			initLibSensCor(90, 60, 99);
			this.weaponName = "whip";
			this.weaponVerb="whipping";
			this.weaponAttack = 10;
			this.weaponPerk = "";
			this.weaponValue = 150;
			this.armorName = "demonic skin";
			this.armorDef = 10;
			this.bonusHP = 700;
			this.lust = 40;
			this.lustVuln = .3;
			this.temperment = TEMPERMENT_LOVE_GRAPPLES;
			this.level = 16;
			this.gems = rand(25) +10;
			this.additionalXP = 50;
			this.drop = NO_DROP;
			this.hornType = HORNS_DRACONIC_X2;
			this.horns = 2;
			this.wingType = WING_TYPE_BAT_LIKE_TINY;
			this.wingDesc = "tiny hidden";
			this.tailType = TAIL_TYPE_DEMONIC;
			this.special1 = kissAttack;
			this.special2 = seduceAttack;
			this.special3 = whipAttack;
			this.drop = NO_DROP;
			checkMonster();
		}

	}

}

license: unknown


code:
package classes.Scenes.Quests.UrtaQuest
{
	import classes.*;
	import classes.GlobalFlags.kGAMECLASS;
	import classes.Scenes.Areas.Desert.Naga;
	import classes.internals.*;

	public class Sirius extends Naga
	{

		override public function eAttack():void
		{
			outputText("Sirius readies his hands, undulating his body erratically with quick motions in order to catch you off-guard and strike at you.\n");
			super.eAttack();
		}

		override protected function outputPlayerDodged(dodge:int):void
		{
			outputText("With your trained eyes, you see through his feints and effectively block his first swipe, then quickly twist your body to kick him away.  He clutches his belly where you kicked him, but recovers quickly, eyes fixated on yours.\n");
		}

		override public function outputAttack(damage:int):void
		{
			if (damage<=0) {
				super.outputAttack(damage);
			} else {
				outputText("You misjudge his pattern and wind up getting slashed by a series of swipes from his sharpened nails.  He distances himself from you in order to avoid retaliation and glares at you with his piercing yellow eyes, a hint of a smile on his face. (" + damage + ")");
			}
		}

		override protected function performCombatAction():void
		{
			var attack:int = rand(4);
			if (player.findStatusEffect(StatusEffects.Blind) >= 0) attack = rand(3);
			if (attack == 0) eAttack();
			if (attack == 1) poisonBite();
			if (attack == 2) manNagaTease();
			if (attack == 3) nagaSpitAttack();
		}

		private function manNagaTease():void
		{
			outputText("The snake-man stares deeply into your eyes, seemingly looking past them, and for a moment your body goes numb.");
//Miss:
			if (rand(10) == 0) {
				outputText("  You blink and shake yourself free of the effects of the snake-man's penetrating gaze.");
				combatRoundOver();
			}
//Hit (Blind):
			if (findStatusEffect(StatusEffects.Blind) >= 0) {
				outputText("  Though your vision is still blurry, you feel yourself being sucked into the golden depths of those pupils, making you forget all your worries, if only for an instant.  All you can focus on is your growing arousal as you sink deeper into his gaze.  You shake your head, clearing your mind of the hypnotising effects the snake-man's eyes seem to possess, though the arousal remains.");
				kGAMECLASS.dynStats("lus", (5 + player.lib / 10 - player.inte / 20));
			}
			//Hit:
			else {
				outputText("  Those pools of yellow suck you into their golden depths, making you forget all your worries, if only for an instant.  All you can focus on is your growing arousal as you sink deeper into his gaze.  You shake your head, clearing your mind of the hypnotising effects the snake-man's eyes seem to possess, though the arousal remains.");
				kGAMECLASS.dynStats("lus", (10 + player.lib / 7 - player.inte / 20));
			}
			combatRoundOver();
		}

		private function nagaSpitAttack():void
		{
			outputText("Hissing loudly, Sirius suddenly curls his lips and spits at your eyes!  ");
//{Hit:
			if (spe / 20 + rand(20) + 1 > player.spe / 20 + 10) {
				outputText("The vile spray hits your eyes and you scream in pain, clawing fiercely at your burning, watering, weeping eyes.  You can't see!  It'll be much harder to fight in this state, but at the same time, his hypnosis won't be so effective...");
				player.createStatusEffect(StatusEffects.Blind, 3, 0, 0, 0);
			}
			//Miss:
			else outputText("You quickly lean to the side, narrowly avoiding being blinded by the snake-man's spit!");
			combatRoundOver();
		}

		private function poisonBite():void
		{
			outputText("With a loud and vicious hiss, Sirius suddenly lunges at you, mouth distended impossibly wide and revealing four needle-like fangs dripping with venom!  ");
//Miss:
			if (player.getEvasionRoll()) {
				outputText("You dodge just in the nick of time, and deliver a punishing blow with the butt of your halberd as Sirius soars past, forcing him to slither past you to make himself ready to defend himself again.");
				combatRoundOver();
			}
//Hit:
			outputText("The snake-man moves too quickly for you to evade and he sinks long fangs into your flesh, leaving a wound that burns with horrific pain. ");
			var damage:Number = 40 + rand(20);
			damage = player.takeDamage(damage, true);
			combatRoundOver();
		}

		override public function defeated(hpVictory:Boolean):void
		{
			game.urtaQuest.urtaBeatsUpSiriusRadio();
		}

		override public function won(hpVictory:Boolean,pcCameWorms:Boolean):void
		{
			game.urtaQuest.urtaLosesToSirriusSnakeRadio();
		}

		public function Sirius()
		{
			super(true);
			this.a = "";
			this.short = "Sirius, a naga hypnotist";
			this.imageName = "sirius";
			this.long = "A strange being with the upper torso of a human man topped with the head of a giant serpent stands before you, hissing in anger and occasionally letting a long, fork-tipped tongue flicker out past his lips.  An imperial-featured masculine human face regards you with an indifferent expression.  A ponytail of deep orange - almost bright red - hair falls down between his shoulders, held together by snake-styled circlets of silver, and matching bracelets of the same material and design adorn his wrists. Scales begin at his lower waist, concealing his manhood from you; he's completely naked otherwise.  His snake body is long and slender, covered in finely meshing scales of a rich orange-red shade, the red broken by a pattern of randomly thick or thin stripes of black.  His burning yellow eyes stare directly into yours, vertical slits of pupils fixated on your own as he undulates and coils in an eerily seductive manner.";
			this.plural = false;
			this.createCock(14,2);
			createBreastRow(0);
			this.ass.analLooseness = ANAL_LOOSENESS_TIGHT;
			this.ass.analWetness = ANAL_WETNESS_DRY;
			this.createStatusEffect(StatusEffects.BonusACapacity,10,0,0,0);
			this.tallness = 5*12+10;
			this.hipRating = HIP_RATING_AMPLE+2;
			this.buttRating = BUTT_RATING_LARGE;
			this.lowerBody = LOWER_BODY_TYPE_NAGA;
			this.skinTone = "mediterranean-toned";
			this.hairColor = "orange";
			this.hairLength = 16;
			initStrTouSpeInte(75, 70, 75, 92);
			initLibSensCor(45, 35, 40);
			this.weaponName = "fangs";
			this.weaponVerb="bite";
			this.weaponAttack = 25;
			this.armorName = "scales";
			this.armorDef = 30;
			this.bonusHP = 400;
			this.lust = 30;
			this.temperment = TEMPERMENT_RANDOM_GRAPPLES;
			this.level = 12;
			this.gems = rand(5) + 8;
			this.drop = NO_DROP;
			this.special1 = nagaPoisonBiteAttack;
			this.special2 = nagaConstrict;
			this.special3 = nagaTailWhip;
			checkMonster();
		}

	}

}


code:
How to work with refactored Scenes, Monsters, and Items?
==============================================================

# Monster classes

`Monster` class represents something player combats with. Its fields are combat params, its methods are attacks and AI.

## Creating new monster

### Basics

Go to Monster constructor, copy its contents, uncomment, and follow the instructions.
There is a number of fields that **MUST** be initialized. If you miss them, you will get a **/!\\BUG** message during
 the combat.

The resulting monster will have a default AI (which is randomly choose between physical attack or one of specials),
will not have any victory/loss rape scenes (but still will drop gems and xp / take gems and 8 hours).

To start the combat with that monster in the scene, just call `startCombat(new MyMonster());`. You can also assign
monster to a variable and modify it.

You also should add the monster to `Scenes/Explore/ExploreDebug.allMonsters` array, so it will be combated in that debug
scene. You can put it in the beginning of the array to quicky test it in debug mode. In that test also check the
inspection and compare it with description.

### Special attacks

Default monsters can have up to 3 special attacks stored in fields `special1`, `special2`, `special3`.
Values could be either 5xxx event codes (old-style, use **ONLY** for existing special) or function references.

Any special attack at all the return points should call `combatRoundOver()` to mark end of monster action.

### Scenes: approach, defeated, won

You might want to write a special Scene class for the monster, which will contain

* approach scene that describes how monster attacks the player and calls `startCombat(new MyMonster())`;
* player victory scene that shows victory rape options.
  Don't forget to call `cleanupAfterCombat()`, `awardPlayer()`, or `finishCombat()` in the end (after the rape/leave).
  The difference is:
    - `cleanupAfterCombat()` calls `awardPlayer()`.
    - `finishCombat()` displays _"You defeat..."_ message and calls `awardPlayer()`.
    - `awardPlayer()` gives player XP and gems, displays messages about it, and resets `gameState` to 0.
* monster victory scene when player is defeated and raped by monster.
  Don't forget to call `cleanupAfterCombat()` in the end (after the rape).

### Overriding AI

To better understand which function to override for monster behaviour customization, here combat call flow is shown:

1. Player selects some combat action (`event 5000`).
2. `enemyAI()` is called, which just contains call to...
    1. `monster.doAI()`, and this method could be overriden. By default:
    2. If monster is stunned, frightened, constricted or otherwise has chance to skip its turn, `monster.handleStun()`,
         `handleFear()`, `handleConstricted()` methods are called. If they `return true`, said effect is ignored.
         1. Their default implementations just
            * display messages like _"your foe is stunned"_ etc;
            * decrease statusAffect round counter by one and until it reaches zero;
            * `return false;` (skip turn).
    3. Somewhere here Exgartuan (if present) gets his chance to comment the situation by `game.exgartuan.exgartuanCombatUpdate()`
    4. From this point monster should decide its action and `Monster.performCombatAction()` (overrideable) is called.
         By default:
    5. A (evenly distributed) random action is chosen from `Monster.eAttack()` and all non-null non-zero `special`1..3.
    6. Description of `special`s was given before, supppose, `Monster.eAttack()` was called from `performCombatAction()`.
         By default:
    7. In case the monster represents a mob, `statusAffectv1(StatusAffects.attacks)` is checked for number of attacks to perform.
         For each attack:
         1. An `Monster.attackSucceeded()` is called, which by default:
            1. If monster is blind, try `Monster.handleBlind()` (`true` means continue attack). Default implementation
                of `handleBlind()` is 2/3 chance to miss and print some message.
            2. Checks `Monster.playerDodged()` which should probably reside in Player class
                1. checks and rolls for `player.speedDodge(monster)`. If `true`, `outputPlayerDodged()`,
                2. checks and rolls for player perks **"Evade"**, **"Misdirection"**, **"Flexibility"**.
         2. If `attackSucceeded()`, do damage with `eOneAttack()`, by default:
            1. Call `calcDamage()`, by default `calcDamage()=player.reduceDamage(eBaseDamage())`
                1. By default, `eBaseDamage()=str+weaponAttack`.
            2. Call `player.takeDamage(damage)`
         3. Call `outputAttack(damage)` to print how severely player is damaged
         4. Call `postAttack(damage)` to perform any post-attack effects
                (currently just raises monster lust if player wears _"barely-decent bondage straps"_).
    8. Finally, `eAttack()` removes status affect **"attacks"**, that means it should be manually set by monster AI
         each round.
    9. Finally finally if combat is not over, show _"Next"_ button.
3. Repeat steps 1-2 until combat is finished. Options are:
    1. `Monster.won()`.
    2. `Monster.defeated()`.
    3. Player flees (`gameState` is reset to 0).
    4. Game over.

#### ^^ WAS TL;DR JUST TELL ME WHAT TO OVERRIDE

See examples:

1. `Imp` for very simple monster with specials
2. `ImpLord extends Imp` for monster that uses special from other monster
3. `GoblinAssassin` for monster with >3 specials
4. `Kiha` for monster that handles fear and blind.
5. `LustyDemons` for mob of monsters with different attacks
6. `Anemone` for monster that deals non-reducable poison damage
7. `Harpy` for monster that display different message for attack blocked by player

## Monster hierarchy

Generally 99% of monsters should subclass classes.Monster directly. However there are cases when several monsters
 share special attacks etc (like male and female spider morphs, also succubi). In that case you can...

1. create abstract
 class with common methods and subclass it (see Scenes/Monsters/AbstractSuccubus and its subclasses MilkySuccubus and
 SecretarialSuccubus.
2. ...however, sometimes you have already configured monster class and you want to add a new variation (example: InfestedHellhound
 extends HellHound). In that case extracting superclass is PITA so I do that thing: I add a to superclass constructor a
 parameter like `noInit:Boolean=false` and if it is `true`, no (or partial) `initXXXX` methods are called. In subclass
 I call `super(true)` and re-init it as I want.
3. The other approach (when monster is a *very* slight modification of another) is just subclass the parent monster
 and after `super()` change some properties/fields to update it. Don't forget to a) change the name. b) to **change**
 gender, you need first call `initGenderless()` to kill the genitals created in superclass and then setup the gender.

## Monster event hooks

If you want to You can set up event hooks that replace default behaviour by setting properties in monster instance.
These hooks are:
* `monster.onWon = Function(hpVictory:Boolean,pcCameWorms:Boolean)` to replace monster-won code. If the field is not null,
 default behaviour is canceled, and you have to finish the combat manually.
* `monster.onDefeated = Function(hpVictory:Boolean)` to replace monster-defeated code. Same as with `onWon`.
* `monster.onPcRunAttempt = Function()` to replace various checks and possible combat end when player hits "Run".

See property docs for more details.

### Note

Event hooks should be used in scenes to modify default monsters, and not in monster classes themselves. Monster classes
should override the functions `won`, `defeated` to change behaviour from default.

# Item classes

Shortname fields and lookups are replaced with `ItemType` instances. Its members are:
* `id`: An unique across all `ItemType`s 7-character identifier that should be kept unchanged in future game versions.
* `shortName`: Currently just a copy of an `id`, but this field is intended to store very short name of the item that could be displayed on buttons instead of id.
* `longName`: Full name of an item.
* `description` A description of an item; currently used in tooltips.
* `value`: Item price.

Remember: **For each item type there should be one and only one instance of `ItemType` class with unique `id`**.
An error will be reported in `trace` if items with same `id`s are created.
`ItemType` instances are usually `const` fields of item libraries (see below).

Saving and loading are done using `id`. To get ItemType by `id`, use `ItemType.lookupItem(id:String):ItemType`.

**Every comparison "is it *that* item?" that looks like `shortName == "ThatItm"` should be
replaced with `itype == library.THATITM` where `library` is item library (see below)**.

## Class hierarchy

1. `ItemType` is superclass for every item. It could be placed into player's inventory or chest.
2. `CommonItem` contains handy methods `outputText`, `clearOutput` and a `game` property to use when performing item
   effects.
3. `Useable` has new method `useItem(player,output,external)` that **MUST** be overriden in subclasses. It is called
   whenever player uses this item, via inventory or *"Use Now"* button. To distinguish these cases, `external` property
   is added: it is `true` when item used not from player's inventory.
    1. `SimpleUseable` is `Useable` defined by constructor parameter `effect`, which is `function(player:Player):void`.
        Examples of such items are armor crafting ingredients and kitsune statue, which display text when used.
4. `Consumable` is a `Useable` that has certain requirements, whether or not it could be used; and if it could (and it is
    not `external`, it removes 1 instance of itself from `player`'s inventory. The superclass method `useItem` is already
    overrided and **MUST NOT** be overriden. Instead, `doEffect(player:Player,output:Boolean)` **MUST** be overriden;
    `canUse(player:Player,output:Boolean)` **COULD** be overriden (default: `return true`).
    1. `SimpleConsumable` is `Consumable` defined by constructor parameter `effect`, which is `function(player:Player):void`.
        \~95% of consumables are instances of `SimpleConsumables`; the rest has custom `canUse`.
5. `Equipable` is a special kind of `Consumable` that is wielded/worn by player. Special effects could be done when
    player equips/unequips `Equipable`. You **MUST NOT** override `doEffect`. Instead, you **MUST** override methods
    * `equip(player:Player,output:Boolean)` that should check whether item could be equipped by player by calling
        `canUse`, unequip item already equipped in that slot, put itself into the slot, and call `equipped(player,output)`
        to call possible equip effect
    * `unequip(player:Player,output:Boolean)` that should remove itself from player's slot and call `unequipped(player,output)`
        to call possible unequip effect.

    Also you **CAN** override methods `equipEffect(player,output)` and `unequipEffect(player,output)` to display
    some messages or add/remove PerkLib. Overrideable method `unequipReturnItem` returns item that should be placed into
    inventory on unequip, or `null` if item simply disappears. Example cases when you need to override this method are:

    * `ComfortableUnderclothes`, `Fists`, and `GooArmor` that return `null`
    * `ComfortableClothes` that return `this` but if the clothes were transformed into others by fetish cultists/zealots
        (which is done by `player.modArmorName`), displays message of them turning into comfortable clothes.
    * Urta's `LeatherArmorSegments` turns into default leather armor on unequip.

    You cannot instantiate `Equipable`, instead, you should use one of the subclasses:

    1. `Armor`. Armor has 3 more properties: `name` (displayable name, shorter than `longName`), `def`, and `perk`.
        `perk` defines armor class: `"Light"`/`"Medium"`/`"Heavy"` but could be empty string.
        Armor is equipped in `player.armor` slot, and when unequipped, is replaced by _"comfortable underclothes"_.
        You can create instances of this class, specify everything you need in the constructor. That armor will have
        no `equipEffect`/`unequipEffect` and could be equipped by anyone.

        * `ArmorWithPerk` is a subclass of `Armor` that adds a player perk on equip and removes in on unequip. Perk
            name and properties are set up in the constructor.

        To fine-tune armor with custom `equipEffect`/`unequipEffect`/`canUse`, or situation-dependent properties,
        subclass it.

    2. `Weapon`. Weapon has 3 more properties: `name` (displayable name, shorter than `longName`), `verb` (like _"hit"_,
        _"slash"_ to use in constructs like `"You "+weapon.verb+" "+monster.name+" with your "+weapon.name`, `attack`,
        and `perk`. `perk` defines weapon class: `"Light"`/`"Heavy"` but could be empty string.
        Weapon is equipped in `player.weapon` slot, and when unequipped, is replaced by _"fists"_.
        You can create instances of this class, specify everything you need in the constructor. That weapon will have
        no `equipEffect`/`unequipEffect` and could be equipped by anyone.

        To fine-tune weapon with custom `equipEffect`/`unequipEffect`/`canUse`, or situation-dependent propertiesm
        subclass it.

Note: `WingStick` though being a weapon, technically is a `Consumable`. Remember that when you check if item is a weapon;
 simple `itype is Weapon` might not be enough. **TODO** `ConsumableWeapon` for javelins, throwing daggers, grenades,
 spell scrolls?

## Item libraries

As mentioned before, only **one** instance of each `ItemType` should be created. Current game architecture suggests them
being `public const` fields of item library classes, and each item library is a `public` field of `CoC` game class.

For examples, see `ConsumableLib` and `CoC.consumables`, `WeaponLib` and `CoC.weapons` etc.

Item libraries usually subclass `BaseContent` to get access to handy methods and create their own handy methods to
 quickly create `ItemType`s for the library. See below.

## Adding new item

### Adding new armor

`ArmorLib` has methods
 `mk(id,shortName,name,longName,def,value,description,perk="")` to create `Armor` and
 `mk2(id,shortName,name,longName,def,value,description,perk,playerPerkName,playerPerkV1,playerPerkV2,playerPerkV3,playerPerkV4,playerPerkDesc)` to create `ArmorWithPerk`.

See examples.

TODO moar on custom armorz

### Adding new weapon

`WeaponLib` has method
 `mk(id,shortName,name,longName,verb,attack,value,description,perk="")` to create `Weapon`.

See examples.

TODO moar on custom weaponz

### Adding new consumable

`ConsumableLib` has method
 `mk(id,shortName,longName,effect,description,value=DEFAULT_VALUE)` to create `SimpleConsumable`.
`effect` should be `function(player:Player):void`.
Legacy consumable effects are stored in `Mutations` class, which is accessible via `m` property.
If you want to have one function to handle different consumables
 (like, `succubiMilk` for both tainted and pure versions),
 declare it with parameters and **`player` argument last**;
 then use `curry` function (see bottom of this readme) to create partial function call
  (e.g. `curry(m.succubiMilk,true)` will return `function(player:Player){m.succubiMilk(true,player)}`.

See examples.

TODO moar on custom consumablez

### Adding new other item

`UseableLib` holds items that are useable but not consumed when used (reagents, kitsune statue).
It has method `mk(id,shortName,longName,effect,description,value=DEFAULT_VALUE)` to create `SimpleUseable`.
`effect` should be `function(player:Player):void`.

See examples.

`MiscItemLib` is currently empty and probably should contain all other kinds of items.

# Scene classes

## Class hierarchy

These are not strict rules but a general directions.

All scenes should be put it BaseContent subclasses. How many classes per event it developer to decide.

An instance of this scene class should be available from `CoC` (declared as field and instantiated in the declaration),
but not necessarily directly. It is preferable that location-specific scenes should be fields of corresponding location
scenes. In code referencing a "foreign" scene to call an event could be something like
`doNext(kGAMECLASS.telAdre.bakeryScene.bakeryuuuuuu);` . For such location-specific scenes it is good to subclass them
from common superclass containing handy methods to access instance of their parent and other helpy stuff (see
_Scenes/Places/TelAdre/TelAdreAbstractContent.as_ )

Due to legacy reasons, if a NPC is combatable, its Monster subclass should be named after him (`Npcname`), and its BaseContent
subclass should be named `Npcname+"Scene"`. However, if a non-combatable NPC (with BaseContent subclass named `npcname`)
becomes combatable in future releases, either its Monster subclass should be named `Npcname+"Combat"`, or the original
`Npcname` should be renamed to `NpcnameScene` and its Monster subclass should be named `Npcname`. Messy.

## Class members

1. Remember that all variables declared in the Scene will not be saved/loaded in any way, or even resetted after save/load
   unless there is specific code for that in global save/load/newgame method.
2. Please keep methods as invisible as possible; a good start would be declare every function private and make them
   public/internal when needed.
3. For debugging purposes methods of all classes in package _classes/Scenes/_ or its subpackages are listed in
   name-by-ref dictionary `funcLookups`, see _engineCore.as_ (Before that only CoC methods were saved in that dictionary).
   If for whatever reason your scene is in another package, add an `[Scene]` metadata to it (see declaration of
   `testContent` in `CoC` for example.

# File placement

## Locations

A **Location** is either **Camp**, **Area**, **Place**, **Dungeon**, or **Quest**.

1. An **Area** is package, which main scene is directly available from **Explore** menu.
2. A **Place** is package, which main scene is available from **Explore** -> **Places** menu, but is not a **Dungeon**.
3. A definitions of **Dungeon** and **Quest** assumed obvious.
4. A BaseContent subclass for general **Area** or **Place** should be placed in either _Scenes/Areas_ or _Scenes/Places_,
   correspondingly.

### Notes

1. **Locations** that share many common scenes could be joined in one package, like **Forest** and **Deepwoods**.
2. Events for **Explore** -> **Explore** should be placed into _Scenes/Explore_.

## NPCs

1. If a **NPC** cannot be discovered directly by visiting **Location**, put it in _Scenes/NPCs_.
2. If a **NPC** can be made a follower/slave/lover/etc, or contains highly detailed dialogue/scene,
   put it in _Scenes/NPCs_.
1. If a **NPC** can be met in a specific **Place** or **Dungeon**, put it in its corresponding package.
3. Else put it in corresponding **Area** package.

## Monsters

1. **Monster** classes that are related to **NPCs** should be placed in same package as corresponding **NPCs**.
2. **Monsters** that mostly could be found in one **Location** should be placed in that **Location** package.
3. Else put it in _Scenes/Monsters_.

## Other scenes

If it does not fit **Camp** scenes, put it whatever it seems logial and where similar scenes may appear.

# Utility functions

During all these refucktorings, I've found `createCallBackFunction` not enough (also, I've moved it to new `Utils` class)
So I've added more functions, (`curry` is enough for most cases):

* `curry(func,...args)` is a partial function call. It returns a function, that will call `func` with first
    arguments already applied: `curry(func,arg1,...,argN)(arg2_1,...,arg2_M) = func(arg1,...,argN,arg2_1,...arg2_M)`.
    For example, `SimpleUseable` accepts `function(player:Player)`, but some of the mutations are parametrized, e.g.
    Incubi Draft could be purified. So we make `function incubiDraft(purified:Boolean,player:Player)`, and to make
    a function reference to impure draft, we use `f=curry(incubiDraft,false)`, and `f(player)` will call
    `incubiDraft(false,player)`.
* `curry(func,arg)` is equivalent of `createCallBackFunction(func,arg)`.
* `lazyIndex(obj,...args)` is a lazy property access. It returns a function, that will dig into `obj`'s `args`
    and return whatever is last: `lazyIndex(obj,arg1,...,argN)()=obj["arg1"]..["argN"]`.
    For example, in cases when `game.telAdre` is not yet initialized (but `game` is), and
    you need to access function reference `game.telAdre.doSomething`, you can use `lazyIndex(game,"telAdre","doSomething")`.
* `lazyCallIndex(func,...args)` is a lazy property access of an unavailable object. It returns a function, that will call
    `func` and dig into result's properties specified by `args`:
    `lazyCallIndex(func,arg1,...,argN)() = func()["arg1"]..["argN"]`.
    Let us enhance previous example and suppose that we need to access same function reference `game.telAdre.doSomething`,
    but even `game` is not initialized. So we make `function getGame(){return game}` and use `lazyCallIndex`:
    `lazyCallindex(getGame,"telAdre","doSomething")`.
* `lazyCallIndexCall(func,...args1)` is the ultimate case when the returned function accepts arguments:
    `lazyCallIndexCall(func,args1_1,...,args1_N)(args2_1,...args2_M) = func()["args1_1"]...["args1_N"](args2_1,...,args2_M)`.
    Example how to use this monstrosity. Previous example, suppose `game.telAdre.doSomething` accepts argument.
    So we can do `f=lazyCallIndexCall(getGame,telAdre,doSomething)` and then `f(bar)` will call `getGame().telAdre.doSomething(bar)`.
* That above example is not type-safe or any kind of safe, so I prefer to use `f=function(bar:Bar){game.telAdre.doSomething(bar)}`


code:
package classes.Scenes.Seasonal
{
	import classes.*;
	import classes.GlobalFlags.*;

	public class XmasBase extends BaseContent
	{
		public var xmasElf:XmasElf = new XmasElf();
		public var xmasMisc:XmasMisc = new XmasMisc();
		public var jackFrost:XmasJackFrost = new XmasJackFrost();
		public var snowAngel:XmasSnowAngel = new XmasSnowAngel();

		public function XmasBase() {}

		public function isItHolidays():Boolean {
			return (date.date >= 25 && date.month == 11 || flags[kFLAGS.ITS_EVERY_DAY] > 0 || player.findPerk(PerkLib.AChristmasCarol) >= 0);
		}

	}

}


code:
package classes.Scenes.Seasonal {

	import classes.*;
	import classes.GlobalFlags.*;

	public class XmasElf extends BaseContent
	{
		public function XmasElf() {}

		public function xmasBitchEncounter():void
		{
			clearOutput();
			spriteSelect(9);
			outputText("Your sleep is disturbed by something repeatedly smacking into your side.  Groggily at first, you grumble and throw back your blanket.  Then you remember where you are, and snap to full wakefulness.  You launch onto your feet, bring up your fists, and stare bewildered at the sight in front of you.\n\n", false);

			outputText("Standing there, innocent as can be, ");
			if (flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] == 0) outputText("is an elf.  She can't be more than four and a half feet tall, and though she has fairly womanly hips, her chest is nothing to speak of.  Her clothing is strange – a red two piece lined with some kind of white fur.  She has typically pointed ears, blond hair, and a red fur-lined cap topped with a white puffball. She's holding a large box in front of her and looking at you expectantly as you stare, dumbfounded.\n\n", false);
			else outputText("is the same elf you met last year.  She can't be more than four and a half feet tall, and though she has fairly womanly hips, her chest is nothing to speak of.  Her clothing is strange – a red two piece lined with some kind of white fur.  She has typically pointed ears, blond hair, and a red fur-lined cap topped with a white puffball. She's holding a large box in front of her and looking at you expectantly as you stare, dumbfounded.\n\n", false);

			outputText("The elf says, \"Hiya " + player.short + "!  I brought you a");
			if (flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] > 0) outputText("nother");
			outputText(" present, straight from the big man himself!\"\n\n", false);

			if (flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] > 0)
			{
				outputText("Confused by her sudden re-appearance, you dumbly ask if you'll be getting the same thing as last year.\n\n");

				outputText("She giggles, \"Oh silly, that would spoil the surprise, wouldn't it?  We've got EVERYONE on our list, even ");
				if (flags[kFLAGS.KELT_BREAK_LEVEL] < 4) outputText("Kelt, though he's getting coal AGAIN");
				else outputText("Kelly, though I think she's getting another big fat dildo");
				outputText(".  You'll get what you're supposed to get!\"\n\n", false);
			}
			else
			{
				outputText("Confused by her appearance and the fact that she already knows you by name, you dumbly ask how she can possibly know who you are.\n\n", false);

				outputText("She giggles, \"Oh silly, don't you know what time of year it is?  We've got EVERYONE on our list, even ");
				if (flags[kFLAGS.KELT_BREAK_LEVEL] < 4) outputText("Kelt, though he's getting coal this year");
				else outputText("Kelly, though I think she's getting a big fat dildo this year");
				outputText(".\"\n\n", false);
			}
			awardAchievement("Naughty or Nice", kACHIEVEMENTS.HOLIDAY_CHRISTMAS_I);
			outputText("You wonder out loud, \"So this... present is mine?\"\n\n", false);
			if (player.cor >= 90 || flags[kFLAGS.JOJO_STATUS] >= 5 || player.findStatusEffect(StatusEffects.Exgartuan) >= 0 || getGame().amilyScene.amilyCorrupt() || flags[kFLAGS.UNKNOWN_FLAG_NUMBER_00283] > 0 || flags[kFLAGS.UNKNOWN_FLAG_NUMBER_00282] > 0 || flags[kFLAGS.NIAMH_STATUS] > 0)
			{
				outputText("She nods, bouncing up and down in excitement and flushing slightly, \"Yup, just tear the lid off and get your gift!\"\n\n", false);
				if (flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] > 0) outputText("Here we go again...\n\n");
				//[Open Present] [Unwrap Elf] [Decline]
				simpleChoices("OpenPresent", openXmasPresent, "", null, "Decline", declineXmasPresent, "", null, "", null);
				return;
			}
			if (player.gender == 0)
			{
				outputText("She nods, bouncing up in down in excitement, \"Yup!  Just open it up!  Are you ready?\"\n\n", false);
				simpleChoices("OpenPresent", openXmasPresent, "", null, "Decline", declineXmasPresent, "", null, "", null);
				return;
			}
			outputText("She nods, bouncing up in down in excitement, \"Yup!  You can unwrap it or unwrap me.  What'll it be?\"\n\n", false);
			//[Open Present] [Unwrap Elf] [Decline]
			simpleChoices("OpenPresent", openXmasPresent, "Unwrap Elf", unwrapElfyPresent, "Decline", declineXmasPresent, "", null, "", null);
		}

		//[Decline]
		public function declineXmasPresent():void {
			spriteSelect(9);
			clearOutput();
			outputText("You shake your head 'no', and inform the elf that you'll have nothing to do with her 'gifts' or 'surprises'.  She looks on the verge of tears as she whines, \"I'm going to get reamed for this!\"\n\n", false);

			outputText("Before you can react, she sprints off into the darkness.", false);
			flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
			doNext(playerMenu);
		}
		//[Open Present]
		public function openXmasPresent():void {
			spriteSelect(9);
			clearOutput();
			outputText("You easily rip through the ribbons holding the box together and pull off the top.   You gasp in ", false);
			if (player.cor >= 90 || flags[kFLAGS.JOJO_STATUS] >= 5 || player.findStatusEffect(StatusEffects.Exgartuan) >= 0 || getGame().amilyScene.amilyCorrupt() || flags[kFLAGS.UNKNOWN_FLAG_NUMBER_00283] > 0 || flags[kFLAGS.UNKNOWN_FLAG_NUMBER_00282] > 0 || flags[kFLAGS.NIAMH_STATUS] > 0) {
				//[Bad Present]
				outputText("shock at the box's contents – a nine inch cock with damn near a dozen buzzing, elliptical devices taped to it.  A pair of coal lumps rattles around underneath it, positioned as if they were the dick's testicles.\n\n", false);

				outputText("Before you can utter a single word of confusion or protest, the elf moans and the cock erupts, spurting a rope of cum into your hair.  The next blast takes you across the nose, then on your lips, then your chin, and finally onto your " + player.allBreastsDescript() + ".  Shocked and dripping, you stand dumbfounded as the elf plants a kiss on your lips, tears off the box, and runs away with her cock flopping and buzzing in time with each step.  There's no way to catch her in this darkness.\n\n", false);

				outputText("The empty 'present' is on the ground with the coal still inside.  You wonder if the coal has any special effect. Everything else in this place does.  In the distance you can hear sleigh bells, and you know it's going to be hard to sleep with all that racket on top of the threat of more intruders...\n\n", false);
				inventory.takeItem(consumables.COAL___, playerMenu);
				flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
			}
			else if (player.cor <= 33) {
				//Great present!
				outputText("surprise at the box's contents - there's a careful arranged set of equipment here, made from woven spider-silk!  Somebody must think you're pretty good.\n\n");
				if (rand(2) == 0) inventory.takeItem(armors.SS_ROBE, playerMenu);
				else inventory.takeItem(armors.SSARMOR, playerMenu);
				flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
			}
			else if (player.cor < 60) {
				//[Good present]
				outputText("surprise at the box's contents – there's a vial labeled gro+.  It looks like it's going to be a 'big' Christmas this year...\n\n", false);
				inventory.takeItem(consumables.GROPLUS, playerMenu);
				flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
			}
			else {
				//[Mediocre Present]
				outputText("surprise at the box's contents – there is a single vial of succubi's delight packed inside.  It's going to be a white Christmas after all...\n\n", false);
				inventory.takeItem(consumables.SDELITE, playerMenu);
				flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
			}
		}

		//[Unwrap the elf]
		public function unwrapElfyPresent():void {
			spriteSelect(9);
			clearOutput();
			outputText("The elf tosses the present to the side and saunters up to you, her hips swaying sensually.  She ", false);
			if (player.tallness > 60) outputText("reaches up and presses herself against you seductively, caressing your body.", false);
			else outputText("cuddles up alongside, happy to have someone of similar stature to seduce.", false);
			outputText("  You find yourself getting more and more aroused as she teases you, sliding around your body as she feels every nook and cranny of your form.  She teases, \"If you don't unwrap a present soon enough I hear it gets taken away, and we don't want that.\"\n\n", false);

			outputText("You ", false);
			if (player.spe < 25) outputText("clumsily ", false);
			else outputText("easily ", false);
			outputText("reach around and grab hold of her fur-lined tube-top, yanking it up over her head in a smooth motion.  Her now exposed breasts are small but well formed.  Her skin is very pale, practically white, and it provides a stark contrast for her hard, cherry-red nipples.   She wiggles happily when you grab her short red skirt and undo the clasp, yanking it off to fully expose her.  The elf's sex is rosy pink in color, and her outer lips are puffy with arousal.   Her slit is completely hairless, and an intricate tattoo of a snowflake sits just above it.  You glance up at her hat and down at her stocking-clad legs and think, 'those can stay.'\n\n", false);

			if (player.gender == 1) dickXmasElfGo();
			else if (player.gender == 2) vagFuckXmasElf();
			else {
				outputText("Which part will you ravish her with?\n\n");
				menu();
				addButton(0,"Male",futaDickXmasElfClr);
				addButton(1,"Female",futaVagXmasElfClr);
			}
		}
		public function futaDickXmasElfClr():void {
			clearOutput();
			dickXmasElfGo();
		}
		public function futaVagXmasElfClr():void {
			clearOutput();
			vagFuckXmasElf();
		}

		public function dickXmasElfGo():void {
			//(Dickfuck)
			if (player.cockArea(0) < 80) {
				outputText("She pushes you down onto your bedroll and whispers, \"Time to enjoy your present.\"\n\n", false);

				outputText("She mounts you without pretense, straddling and inserting your " + player.cockDescript(0) + " in one smooth motion.  The sudden change from cool, night air to hot, tight pussy sends shockwaves of pleasure into your skull.  You master yourself before your eyes roll the whole way back and close your mouth before you start drooling.   Her vise-like tightness is inhuman, but somehow not so tight as to be uncomfortable.   The internal muscles clench and squeeze around you with an uncommon degree of control.  She's so hot, wet, and tight that you shiver.  You start rocking underneath her, giving in completely to the pleasure of her hole.\n\n", false);

				outputText("You grunt, pistoning into her over and over.  She clears her throat as she's bouncing atop of you, and you look back up, suddenly reminded that there's more to the world than the cunt milking your " + player.cockDescript(0) + ".  The elf explains, \"Don't be ashamed.  We elves have magical cunts.  Once something is inside it'll feel so good that it never wants to leave.  Judging from the look on your face I don't think you ever want to leave, do you?  I'm the best present you've ever had, aren't I?  Go ahead, cum for me, show me what a great gift I am.\"\n\n", false);

				outputText("She's absolutely right – there's some indescribably pleasurable thing about the heat radiating into your dick that makes it feel like it's about to melt and pass into heaven.  The elf giggles and the vibrations of her laugh somehow radiate into you, and it's just too much.  You cum for your present, submitting to her pleasure as your spooge boils up into her.   It squelches wetly as it pumps into her, sounding absolutely perverse.", false);
				if (player.cumQ() >= 250) outputText("  The spunk quickly fills her womb and flows back out her entrance, frothing and bubbling as it drips over your " + player.hipDescript() + ".  ", false);
				if (player.cumQ() >= 1000) outputText("  It begins to splatter everywhere as you pour out more and more, the elf looking on with amusement as her cunt turns into a cum-spraying fountain.  ", false);
				outputText("\n\n", false);

				outputText("Once your orgasm ends the elf begins gyrating her hips again, her pussy frothing and dripping a mixed batch of creamy cum.   You don't go soft.  If anything you get even harder and more sensitive.  Brain blasting pressure squeezes up your rod from the elf's cunt as she starts bouncing again, fucking you in earnest, \"I told you my cunt was magical.  You'll never go soft inside me – your cum fuels my magic and makes you feel even better.\"\n\n", false);

				outputText("Aside from your " + player.cockDescript(0) + ", your body has gone completely numb from the waist down.  You glance down and see your " + player.legs() + " twitching and convulsing under the elf's assault.   She's so hot inside, it's like her pussy's candy-coated in liquid pleasure.   You fuck her harder and harder, squeezing her hips tightly and roughly fucking her magical pussy.   Somehow you're on the edge again, about to unload.  You start counting in your head, trying to resist another orgasm.  You know if you do you'll never be able stop.  You doubt you'll even be able to think.\n\n", false);

				outputText("Your effort at holding out totally fails – you start counting in time with each thrust, tying the numbers into the feel of the velvet cock-sleeve as it massages your " + player.cockDescript(0) + ".   The elf smiles condescendingly and taunts, \"I can see you've already lost the ability to resist the pleasure.  Just give in, and enjoy the night.  I'll be riding you 'til morning.\"\n\n", false);

				outputText("It's too hot, oh gods it's too hot.  You cum again, splattering her womb with more seed.  The elf's skin flushes as you pump more into her, squirting more and more into her overfull entrance.  Miraculously, you cum just as much as before, ", false);
				if (player.cumQ() >= 250) outputText("dumping out more and more waves of jizm until you're lying in a deep puddle of it, ", false);
				outputText("and somehow the orgasm lasts on even after you've emptied.   Your eyes roll back for a moment as you nearly lose consciousness.\n\n", false);

				outputText("You snap out of it and the elf is smirking down at you, stationary.  You feel totally numb – your " + player.cockDescript(0) + " has all of your sensation, all of your sense of touch.   On their own, your " + player.hipDescript() + " continually rise and fall, pumping into her with noisy explosions of pleasure that leave you gasping and writhing.  Every time you start to think something, the vise-like tunnel slides down you and squeezes your " + player.cockDescript(0) + ", interrupting any attempt at thought.  You give up on thinking and start drooling all over yourself, your world fading into a heaven of constant pleasure and repeated orgasms.\n\n", false);

				outputText("The elf fucks you relentlessly for hours, forcing you to cum over and over.  Somehow you never go dry, and each time feels better than the last.  Your bedroll is soaked with cum, your body is exhausted, and the elf FINALLY cums with a high-pitched cry of orgasmic pleasure.  Her body quakes, and you cum again, squirting messily inside her again.  The vise of pleasure on you quivers and squeezes, growing hotter by the second as the elf's orgasm drags on and on, milking you of every drop and setting you in a feedback loop of infinite pleasure.  You black out.", false);
			}
			else {
				//(TOO BIG)
				outputText("She pushes you down onto your bedroll and whispers, \"Time to enjoy your present.\"\n\n", false);
				outputText("The elf grabs ahold of your " + player.cockDescript(0) + " with both hands and cuddles against it as if it were a person, planting kisses along the edge of its " + player.cockHead() + ".  She laughs, \"Oh my, you're so big!  I almost wish I was big enough to take this bad boy.  Believe me, you haven't lived until you've been milked by an elf's cunt.\"\n\n", false);

				outputText("She wraps her arms around it and begins licking it, squatting down and standing up, jerking you off with her whole body.  Each time her cute bottom bumps your " + player.allBreastsDescript() + " ", false);
				if (player.biggestTitSize() >= 2) outputText("making them jiggle", false);
				else outputText("making her tight butt give a tiny jiggle", false);
				outputText(".  She hums happily as she works at the task, slathering it in spit, pressing her moist cunt against you.   Her warm body sliding along you feels fantastic, and feeling a bit daring, you give her a light slap on the ass-cheek.\n\n", false);

				outputText("The elf looks over her shoulder and laughs, \"Someone is feeling a bit naughty.  Well, I guess I'll have to help you drain out all that naughty energy.\"\n\n", false);

				outputText("Before you can puzzle out her meaning, she takes a big gulp of air, grabs your " + player.cockHead() + " with both hands, and presses her lips into your urethra.  She blows into it with a look of intense concentration.  You can feel your urethra filling, expanding with something, but it feels more like liquid than air, tingling as it slides deep into your shaft towards your ", false);
				if (player.balls > 0) outputText("balls", false);
				else if (player.hasSheath()) outputText("sheath", false);
				else outputText("body", false);
				outputText(".   She blows and blows, seemingly filling you with an inexhaustible supply of whatever magical substance she's forcing inside you. The tingling grows stronger and stronger, and then changes to warmth as a pleasurable heat centers itself in your midsection.\n\n", false);

				outputText("The magic-using elf pulls back with a knowing grin and resumes stroking you, ignoring a dribble of pink fluid that squirts from your tip.   The warmth inside builds higher and you start sweating, even in the cool night air. The uncomfortable heat churns inside you", false);
				if (player.balls > 0) outputText("r " + player.ballsDescriptLight(), false);
				outputText(", a gentle pressure that builds higher and higher until you feel about to explode.  You need to cum, and you squirm in the elf's grasp, trembling and shuddering as one of her hands slips over a particularly sensitive spot. A bead of pre-cum rolls out of your " + player.cockHead() + " and starts sliding down the shaft, followed by another, and another, and another.\n\n", false);

				outputText("Your 'present' asks with gradually rising authority, \"Do you feel the naughtyness leaking out?  It feels good doesn't it?  Yes it does, but that's just the start.  You've got a lot of pent up naughty that needs to come out so you'll be good and see me next year.  So be a good boy and cum out all those bad thoughts for me please.\"\n\n", false);

				outputText("She flips around to the far side of your dick and hugs it tightly, squeezing it from base to tip in a fluid motion makes your abdominals clench with unexpected orgasm.   The first 'squirt' of cum is more like a geyser going off.  ", false);
				if (player.cumQ() < 500) outputText("You recoil from shooting out so much – it's far and away more than you're normally capable of.  ", false);
				outputText("The elf hugs it and squeezes tightly while whispering, \"Naughty naughty.\"\n\n", false);

				outputText("Thick ropes of your orgasmic goop splatter into her hair, and each successive blast comes out with less and less force, until you're leaking a steady stream of cum that rolls down your " + player.cockDescript(0) + " and soaks the pointy-eared woman completely.   As you release your prodigious load the scent of cinnamon fills the air, and you dumbly wonder if it's some side effect of the magic she used on you.  Regardless, cum keeps leaking out over the elf and onto you, and you eventually lose consciousness from perpetual orgasm.", false);
			}
			//(Go to followup for fucking scene)
			//[Next]
			doNext(xmasFuckFollowup);
			player.orgasm();
		}

		//[FEMALE SCENE]
		public function vagFuckXmasElf():void {
			outputText("She pushes you down onto your bedroll and whispers, \"Time to enjoy your present.\"\n\n", false);
			outputText("The elf winks and spreads her legs, revealing her obviously aroused sex to you.  She winks and you see her muscles clench.  The moist lips of her vagina slowly spread apart, and a blunt white object begins to squeeze out.  Is she laying an egg?  Wait- no, more of the object slides out and you can see now that it's tubular in shape, like some sort of sex-toy, and it's covered in a spiraling red pattern.  The object continues its slow journey downwards, roughly six inches hanging free as the elf grunts and moans, her face flushed.   She grips it with both hands and pulls it slowly.  It reminds you the soldiers in training back home the first time they tried to draw a sword – a mix of awkwardness and excitement.\n\n", false);

			outputText("In seconds the elf has her hands around a red-striped double-sided dildo.  It wiggles back and forth obscenely, and now that you have a good look at it, you realize the red sections are slightly raised, to better stimulate the user.  She pants and runs her hand over its pussy-slicked surface, shivering in remembered pleasure until her attention returns to you.  Her lips curl into a knowing smile and she kneels between your " + player.legs() + ", spreading them apart for better access to your " + player.vaginaDescript(0) + ".\n\n", false);

			outputText("The diminutive elf rubs the tip over your lower lips and " + player.clitDescript() + " a few times, getting you nice and hot before she slides it up your " + player.vaginaDescript(0) + ".  The dildo feels wonderful inside, each curved ridge sending shivers up your spine as it enters you, then stroking along your walls as you take it deeper and deeper.  The motion is interrupted once your 'present' has decided she's lodged her candy-cane-like toy deep enough inside you.  She lies back and scoots forwards, taking the rest of the striped dildo into her hairless snatch until your mounds are locked together, feminine fluids mixing on an artificial cock.");
			player.cuntChange(15,true,true,false);
			outputText("\n\n", false);

			outputText("The elf giggles, \"Merry Christmas,\" as she starts rocking against you.  The dildo slides through your passage, massaging your inner walls and bumping against your " + player.clitDescript() + "'s underside with each stroke.   She's got such great muscle control that she's clamped down on the double-sided dildo and started using it as a cock to fuck you!  She smirks and pounds your vulnerable " + player.vaginaDescript(0) + ", raping it with increasingly forceful strokes.  You grunt and moan as each stroke loudly smacks into your hips.  You feel yourself closing in on an orgasm, but the elf-girl relaxes her grip and simply grinds against you, taking the stimulation down a notch.\n\n", false);

			outputText("Determined to get off, you wiggle against her, mashing your " + player.clitDescript() + " into her own.  She squirms and cries out, actually getting off before you!  You muse that elves must have extraordinarily sensitive clitorises, but before you can act on it, you feel a sudden stirring in your loins.   The dildo is starting to spin!  You prop yourself up and watch, unbelieving as the elf's orgasmic contractions visibly contort her belly, moving more and more quickly as the spinning speeds up.  In seconds the twirling assault has placed you back on the edge of orgasm, and you're groaning and rubbing against your insensate lover for more.\n\n", false);

			outputText("You cum, ", false);
			if (player.vaginas[0].vaginalWetness == VAGINA_WETNESS_SLAVERING) outputText("gushing fluids", false);
			else if (player.vaginas[0].vaginalWetness >= VAGINA_WETNESS_SLICK) outputText("dripping fluids", false);
			else outputText("squishing wetly", false);
			outputText(" as your " + player.vaginaDescript(0) + " is drilled by the elf's double-ended dong.   It feels beyond good, like having a cock inside you that rubs against each part of your pussy over and over and over without the barest hint of mercy.  Your gasp and pant, glancing back up at the elf.  She's already recovered from her orgasm, though she has an intense look of concentration on her face while she focuses on twisting the dildo inside you.\n\n", false);

			outputText("\"You don't think I'd let you cum just once did you?  I'm going to drill all the naughty, sinful little thoughts from your slut-hole!\"\n\n", false);

			outputText("You throw your head back and let out a low shuddering moan as she spins the dildo even faster, forcing your convulsing cunt to stay locked in a mind-shattering orgasm.  Eyes crossed, you collapse onto your back and twitch, body wriggling and flopping about nervelessly as it caves in to pleasure it was never meant to handle.\n\n", false);

			outputText("You black out to the following words: \"Good girl.  Keep cumming, let out all those naughty thoughts.  I can't wait to see you next year!\"", false);
			doNext(xmasFuckFollowupFems);
			player.orgasm();
		}

		//MANTASTIC FOLLOWUP:
		public function xmasFuckFollowup():void {
			hideUpDown();
			clearOutput();
			outputText("You awaken in the morning, sore and exhausted, but more satisfied than you've ever felt before.  Your body feels INCREDIBLY sensitive from head to toe, but particularly on your well-used " + player.cockDescript(0) + ".  In spite of the traumatic lovemaking, you feel remarkably clear-headed.\n\n", false);
			outputText("Did you enjoy being able to cum so much");
			if (player.findPerk(PerkLib.ElvenBounty) >= 0) outputText(" again");
			outputText("?", false);
			//[Yes][No] – yes awards (+250 mls cum volume), no awards +15 intellect
			doYesNo(xmasPerkM,xmasSmart);
			//(-5 corruption)
			dynStats("cor", -5);
			//(+20 sens unless it would bring you over 80 sens, then +5 sens)
			if (player.sens + 20 > 80) dynStats("sen", 5);
			else dynStats("sen", 15);
			temp = 1001;
			flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
		}
		//FEMTASTIC FOLLOWUP:
		public function xmasFuckFollowupFems():void {
			hideUpDown();
			clearOutput();
			outputText("You awaken in the morning, sore and exhausted, but more satisfied than you've ever felt before.  Your body feels INCREDIBLY sensitive from head to toe, but particularly in your well-used " + player.vaginaDescript(0) + ".  In spite of the traumatic lovemaking, you feel remarkably clear-headed.  The dildo appears to have completely dissolved inside you, leaving behind a pinkish fluid that drips from your lips.\n\n", false);

			outputText("Do you think it might have done anything to you");
			if (player.findPerk(PerkLib.ElvenBounty) >= 0) outputText(" again");
			outputText("?", false);
			//[Yes][No] – yes awards (+15 fertility!), no awards +15 intellect
			doYesNo(xmasPerkM,xmasSmart);
			//(-5 corruption)
			dynStats("cor", -5);
			//(+20 sens unless it would bring you over 80 sens, then +5 sens)
			if (player.sens + 20 > 80) dynStats("sen", 5);
			else dynStats("sen", 15);
			temp = 2002;
			flags[kFLAGS.PC_ENCOUNTERED_CHRISTMAS_ELF_BEFORE] = date.fullYear;
		}

		public function xmasPerkM():void {
			if (player.findPerk(PerkLib.ElvenBounty) < 0) {
				if (temp == 1001) player.createPerk(PerkLib.ElvenBounty,250,0,0,0);
				else player.createPerk(PerkLib.ElvenBounty,0,15,0,0);
				outputText("New Perk Acquired - Elven Bounty!", true);
			}
			else {
				clearOutput();
				outputText("Perk Enhanced - Elven Bounty!");
				if (temp == 1001) {
					player.addPerkValue(PerkLib.ElvenBounty,1,250);
					outputText(" - +250mL cum production!");
				}
				else {
					player.addPerkValue(PerkLib.ElvenBounty,2,15);
					outputText(" - +15 bonus fertility!");
				}

			}
			doNext(playerMenu);
		}
		public function xmasSmart():void {
			hideUpDown();
			outputText("You nod to yourself, feeling pretty smart about your decision.", true);
			doNext(playerMenu);
			dynStats("int", 15);
		}
	}
}


code:
package classes
{
	public class StatusEffectClass
	{
		//constructor
		public function StatusEffectClass(stype:StatusEffectType,value1:Number=0,value2:Number=0,value3:Number=0,value4:Number=0)
		{
			this._stype = stype;
			this.value1 = value1;
			this.value2 = value2;
			this.value3 = value3;
			this.value4 = value4;
		}
		//data
		private var _stype:StatusEffectType;
		public var value1:Number;
		public var value2:Number;
		public var value3:Number;
		public var value4:Number;
		//MEMBER FUNCTIONS
		public function get stype():StatusEffectType
		{
			return _stype;
		}

		public function toString():String
		{
			return "["+_stype+","+value1+","+value2+","+value3+","+value4+"]";
		}
	}
}


code:
/**
 * Created by aimozg on 31.01.14.
 */
package classes
{
	import flash.utils.Dictionary;

	public class StatusEffectType
	{
			private static var STATUSAFFECT_LIBRARY:Dictionary = new Dictionary();

			public static function lookupStatusEffect(id:String):StatusEffectType{
				return STATUSAFFECT_LIBRARY[id];
			}

			public static function getStatusEffectLibrary():Dictionary
			{
				return STATUSAFFECT_LIBRARY;
			}

			private var _id:String;

			/**
			 * Unique perk id, should be kept in future game versions
			 */
			public function get id():String
			{
				return _id;
			}

			public function StatusEffectType(id:String)
			{
				this._id = id;
				if (STATUSAFFECT_LIBRARY[id] != null) {
					CoC_Settings.error("Duplicate status affect "+id);
				}
				STATUSAFFECT_LIBRARY[id] = this;
			}

			public function toString():String
			{
				return "\""+_id+"\"";
			}
		}
}


code:
package classes
{
	import classes.StatusEffects.CombatStatusEffect;

	/**
	 * IMPORTANT NOTE:
	 * You can rename the constants BUT NOT the string ids (they are stored in saves).
	 */
	public class StatusEffects
	{
		// Non-combat player perks
		public static const AllNaturalOnaholeUsed:StatusEffectType = mk("all-natural onahole used");
		public static const AndysSmoke:StatusEffectType = mk("Andy's Smoke"); //v1: Hours; v2: Speed; v3: Intelligence
		public static const AteEgg:StatusEffectType = mk("ateEgg");
		public static const AnemoneArousal:StatusEffectType = mk("Anemone Arousal");
		public static const BimboChampagne:StatusEffectType = mk("Bimbo Champagne");
		public static const Birthed:StatusEffectType = mk("Birthed");
		public static const BirthedImps:StatusEffectType = mk("Birthed Imps");
		public static const BlackCatBeer:StatusEffectType = mk("Black Cat Beer");
		public static const BlackNipples:StatusEffectType = mk("Black Nipples");
		public static const BlowjobOn:StatusEffectType = mk("BlowjobOn");
		public static const BoatDiscovery:StatusEffectType = mk("Boat Discovery");
		public static const BonusACapacity:StatusEffectType = mk("Bonus aCapacity");
		public static const BonusVCapacity:StatusEffectType = mk("Bonus vCapacity");
		public static const BottledMilk:StatusEffectType = mk("Bottled Milk");
		public static const BreastsMilked:StatusEffectType = mk("Breasts Milked");
		public static const BSwordBroken:StatusEffectType = mk("BSwordBroken");
		public static const BuiltMilker:StatusEffectType = mk("BUILT: Milker");
		public static const BurpChanged:StatusEffectType = mk("Burp Changed");
		public static const ButtStretched:StatusEffectType = mk("ButtStretched");
		public static const CampAnemoneTrigger:StatusEffectType = mk("Camp Anemone Trigger");
		public static const CampMarble:StatusEffectType = mk("Camp Marble");
		public static const CampRathazul:StatusEffectType = mk("Camp Rathazul");
		public static const ClaraCombatRounds:StatusEffectType = mk("Clara Combat Rounds");
		public static const ClaraFoughtInCamp:StatusEffectType = mk("Clara Fought In Camp");
		public static const CockPumped:StatusEffectType = mk("Cock Pumped");
		public static const Contraceptives:StatusEffectType = mk("Contraceptives");
		public static const CuntStretched:StatusEffectType = mk("CuntStretched");
		public static const DefenseCanopy:StatusEffectType = mk("Defense: Canopy");
		public static const DeluxeOnaholeUsed:StatusEffectType = mk("deluxe onahole used");
		public static const DogWarning:StatusEffectType = mk("dog warning");
		public static const DragonBreathBoost:StatusEffectType = mk("Dragon Breath Boost");
		public static const DragonBreathCooldown:StatusEffectType = mk("Dragon Breath Cooldown");
		public static const Dysfunction:StatusEffectType = mk("dysfunction");
		public static const Edryn:StatusEffectType = mk("Edryn");
		public static const Eggchest:StatusEffectType = mk("eggchest");
		public static const Eggs:StatusEffectType = mk("eggs");
		public static const EmberFuckCooldown:StatusEffectType = mk("ember fuck cooldown");
		public static const EmberMilk:StatusEffectType = mk("Ember's Milk");
		public static const EmberNapping:StatusEffectType = mk("Ember Napping");
		public static const EverRapedJojo:StatusEffectType = mk("Ever Raped Jojo");
		public static const Exgartuan:StatusEffectType = mk("Exgartuan");
		public static const ExploredDeepwoods:StatusEffectType = mk("exploredDeepwoods");
		public static const FaerieFemFuck:StatusEffectType = mk("Faerie Fem Fuck");
		public static const FaerieFucked:StatusEffectType = mk("Faerie Fucked");
		public static const FappedGenderless:StatusEffectType = mk("fapped genderless");
		public static const Feeder:StatusEffectType = mk("Feeder");
		public static const Fertilized:StatusEffectType = mk("Fertilized");
		public static const FetishOn:StatusEffectType = mk("fetishON");
		public static const FuckedMarble:StatusEffectType = mk("FuckedMarble");
		public static const Fullness:StatusEffectType = mk("Fullness"); //Alternative to hunger
		public static const Goojob:StatusEffectType = mk("GOOJOB");
		public static const GooStuffed:StatusEffectType = mk("gooStuffed");
		public static const Groundpound:StatusEffectType = mk("Groundpound");
		public static const HairdresserMeeting:StatusEffectType = mk("hairdresser meeting");
		public static const Hangover:StatusEffectType = mk("Hangover");
		public static const Heat:StatusEffectType = mk("heat");
		public static const HorseWarning:StatusEffectType = mk("horse warning");
		public static const ImmolationSpell:StatusEffectType = mk("Immolation Spell");
		public static const ImpGangBang:StatusEffectType = mk("Imp GangBang");
		public static const Infested:StatusEffectType = mk("infested");
		public static const IzmaBlowing:StatusEffectType = mk("IzmaBlowing");
		public static const IzumisPipeSmoke:StatusEffectType = mk("Izumis Pipe Smoke");
		public static const JerkingIzma:StatusEffectType = mk("JerkingIzma");
		public static const Jizzpants:StatusEffectType = mk("Jizzpants");
		public static const JojoMeditationCount:StatusEffectType = mk("Jojo Meditation Count");
		public static const JojoNightWatch:StatusEffectType = mk("JojoNightWatch");
		public static const JojoTFOffer:StatusEffectType = mk("JojoTFOffer");
		public static const Kelt:StatusEffectType = mk("Kelt");
		public static const KeltBJ:StatusEffectType = mk("KeltBJ");
		public static const KeltBadEndWarning:StatusEffectType = mk("Kelt Bad End Warning");
		public static const KeltOff:StatusEffectType = mk("KeltOff");
		public static const KnowsArouse:StatusEffectType = mk("Knows Arouse");
		public static const KnowsBlind:StatusEffectType = mk("Knows Blind");
		public static const KnowsCharge:StatusEffectType = mk("Knows Charge");
		public static const KnowsHeal:StatusEffectType = mk("Knows Heal");
		public static const KnowsMight:StatusEffectType = mk("Knows Might");
		public static const KnowsWhitefire:StatusEffectType = mk("Knows Whitefire");
		public static const LactationEndurance:StatusEffectType = mk("Lactation Endurance");
		public static const LactationReduction:StatusEffectType = mk("Lactation Reduction");
		public static const LactationReduc0:StatusEffectType = mk("Lactation Reduc0");
		public static const LactationReduc1:StatusEffectType = mk("Lactation Reduc1");
		public static const LactationReduc2:StatusEffectType = mk("Lactation Reduc2");
		public static const LactationReduc3:StatusEffectType = mk("Lactation Reduc3");
		public static const LootEgg:StatusEffectType = mk("lootEgg");
		public static const LostVillagerSpecial:StatusEffectType = mk("lostVillagerSpecial");
		public static const Luststick:StatusEffectType = mk("Luststick");
		public static const LustStickApplied:StatusEffectType = mk("Lust Stick Applied");
		public static const LustyTongue:StatusEffectType = mk("LustyTongue");
		public static const MalonVisitedPostAddiction:StatusEffectType = mk("Malon Visited Post Addiction");
		public static const Marble:StatusEffectType = mk("Marble");
		public static const MarbleHasItem:StatusEffectType = mk("MarbleHasItem");
		public static const MarbleItemCooldown:StatusEffectType = mk("MarbleItemCooldown");
		public static const MarbleRapeAttempted:StatusEffectType = mk("Marble Rape Attempted");
		public static const MarblesMilk:StatusEffectType = mk("Marbles Milk");
		public static const MarbleSpecials:StatusEffectType = mk("MarbleSpecials");
		public static const MarbleWithdrawl:StatusEffectType = mk("MarbleWithdrawl");
		public static const Meditated:StatusEffectType = mk("Meditated"); // DEPRECATED
		public static const MeanToNaga:StatusEffectType = mk("MeanToNaga");
		public static const MeetWanderer:StatusEffectType = mk("meet wanderer");
		public static const MetRathazul:StatusEffectType = mk("metRathazul");
		public static const MetWorms:StatusEffectType = mk("metWorms");
		public static const MetWhitney:StatusEffectType = mk("Met Whitney");
		public static const Milked:StatusEffectType = mk("Milked");
		public static const MinoPlusCowgirl:StatusEffectType = mk("Mino + Cowgirl");
		public static const Naga:StatusEffectType = mk("Naga");
		public static const NakedOn:StatusEffectType = mk("NakedOn");
		public static const NoJojo:StatusEffectType = mk("noJojo");
		public static const NoMoreMarble:StatusEffectType = mk("No More Marble");
		public static const Oswald:StatusEffectType = mk("Oswald");
		public static const ParasiteSlug:StatusEffectType = mk("infected by slug parasite");
		public static const ParasiteSlugReproduction:StatusEffectType = mk("slug parasite reproducing");
		public static const ParasiteSlugMet:StatusEffectType = mk("met a parasite in the bog");
		public static const ParasiteSlugMusk:StatusEffectType = mk("Smell that musk man");
		public static const ParasiteSlugMatureDay:StatusEffectType = mk("sets a delay before parasite can reproduce after maturing");
		public static const PlainOnaholeUsed:StatusEffectType = mk("plain onahole used");
		public static const PhoukaWhiskeyAffect:StatusEffectType = mk("PhoukaWhiskeyAffect");
		public static const PostAkbalSubmission:StatusEffectType = mk("Post Akbal Submission");
		public static const PostAnemoneBeatdown:StatusEffectType = mk("Post Anemone Beatdown");
		public static const PureCampJojo:StatusEffectType = mk("PureCampJojo");
		public static const RathazulArmor:StatusEffectType = mk("RathazulArmor");
		public static const RepeatSuccubi:StatusEffectType = mk("repeatSuccubi");
		public static const Rut:StatusEffectType = mk("rut");
		public static const SharkGirl:StatusEffectType = mk("Shark-Girl");
		public static const ShieldingSpell:StatusEffectType = mk("Shielding Spell");
		public static const SlimeCraving:StatusEffectType = mk("Slime Craving");
		public static const SlimeCravingFeed:StatusEffectType = mk("Slime Craving Feed");
		public static const SlimeCravingOutput:StatusEffectType = mk("Slime Craving Output");
		public static const SuccubiFirst:StatusEffectType = mk("SuccubiFirst");
		public static const SuccubiNight:StatusEffectType = mk("succubiNight");
		public static const TakenGroPlus:StatusEffectType = mk("TakenGro+");
		public static const TakenLactaid:StatusEffectType = mk("TakenLactaid");
		public static const Tamani:StatusEffectType = mk("Tamani");									//Used only for compatibility with old save files, otherwise no longer in use
		public static const TamaniFemaleEncounter:StatusEffectType = mk("Tamani Female Encounter");	//Used only for compatibility with old save files, otherwise no longer in use
		public static const TelAdre:StatusEffectType = mk("Tel'Adre");
		public static const TentacleBadEndCounter:StatusEffectType = mk("TentacleBadEndCounter");
		public static const TentacleJojo:StatusEffectType = mk("Tentacle Jojo");
		public static const TensionReleased:StatusEffectType = mk("TensionReleased");
		public static const TF2:StatusEffectType = mk("TF2");
		public static const TookBlessedSword:StatusEffectType = mk("Took Blessed Sword");

		//Old status plots. DEPRECATED, DO NOT USE. Currently cannot be removed without breaking existing saves.
		public static const DungeonShutDown:StatusEffectType = mk("DungeonShutDown");
		public static const FactoryOmnibusDefeated:StatusEffectType = mk("FactoryOmnibusDefeated");
		public static const FactoryOverload:StatusEffectType = mk("FactoryOverload");
		public static const FactoryIncubusDefeated:StatusEffectType = mk("FactoryIncubusDefeated");
		public static const FoundFactory:StatusEffectType = mk("Found Factory");
		public static const IncubusBribed:StatusEffectType = mk("IncubusBribed");
		public static const FactorySuccubusDefeated:StatusEffectType = mk("FactorySuccubusDefeated");
		public static const MaraeComplete:StatusEffectType = mk("Marae Complete");
		public static const MaraesLethicite:StatusEffectType = mk("Marae's Lethicite");
		public static const MaraesQuestStart:StatusEffectType = mk("Marae's Quest Start");
		public static const MetCorruptMarae:StatusEffectType = mk("Met Corrupt Marae");
		public static const MetMarae:StatusEffectType = mk("Met Marae");

		//Prisoner status effects.
		public static const PrisonCaptorEllyStatus:StatusEffectType = mk("prisonCaptorEllyStatus");
		public static const PrisonCaptorEllyQuest:StatusEffectType = mk("prisonCaptorEllyQuest");
		public static const PrisonCaptorEllyPet:StatusEffectType = mk("prisonCaptorEllyPet");
		public static const PrisonCaptorEllyBillie:StatusEffectType = mk("prisonCaptorEllyBillie");
		public static const PrisonCaptorEllyScruffy:StatusEffectType = mk("prisonCaptorEllyScruffy");
		public static const PrisonRestraints:StatusEffectType = mk("prisonRestraint");
		public static const PrisonCaptorEllyScratch:StatusEffectType = mk("prisonCaptorEllyScatch");

		public static const UmasMassage:StatusEffectType = mk("Uma's Massage"); //v1 = bonus index; v2 = bonus value; v3 = remaining time
		public static const Uniball:StatusEffectType = mk("Uniball");
		public static const UsedNaturalSelfStim:StatusEffectType = mk("used natural self-stim");
		public static const used_self_dash_stim:StatusEffectType = mk("used self-stim");
		public static const Victoria:StatusEffectType = mk("Victoria");
		public static const VoluntaryDemonpack:StatusEffectType = mk("Voluntary Demonpack");
		public static const WormOffer:StatusEffectType = mk("WormOffer");
		public static const WormPlugged:StatusEffectType = mk("worm plugged");
		public static const WormsHalf:StatusEffectType = mk("wormsHalf");
		public static const WormsOff:StatusEffectType = mk("wormsOff");
		public static const WormsOn:StatusEffectType = mk("wormsOn");
		public static const WandererDemon:StatusEffectType = mk("wanderer demon");
		public static const WandererHuman:StatusEffectType = mk("wanderer human");
		public static const Yara:StatusEffectType = mk("Yara");

		// monster
		public static const Attacks:StatusEffectType = mk("attacks");
		public static const BimboBrawl:StatusEffectType = mk("bimboBrawl");
		public static const BowCooldown:StatusEffectType = mk("Bow Cooldown");
		public static const BowDisabled:StatusEffectType = mk("Bow Disabled");
		public static const Charged:StatusEffectType = mk("Charged");
		public static const Climbed:StatusEffectType = mk("Climbed");
		public static const Concentration:StatusEffectType = mk("Concentration");
		public static const Constricted:StatusEffectType = mk("Constricted");
		public static const CoonWhip:StatusEffectType = mk("Coon Whip");
		public static const Counter:StatusEffectType = mk("Counter");
		public static const DomFight:StatusEffectType = mk("domfight");
		public static const DrankMinoCum:StatusEffectType = mk("drank mino cum");
		public static const DrankMinoCum2:StatusEffectType = mk("drank mino cum2")
		public static const Drunk:StatusEffectType = mk("Drunk");
		public static const Earthshield:StatusEffectType = mk("Earthshield");
		public static const Fear:StatusEffectType = mk("Fear");
		//public static const FearCounter:StatusEffectType = mk("FearCounter");
		public static const GenericRunDisabled:StatusEffectType = mk("Generic Run Disabled");
		public static const Gigafire:StatusEffectType = mk("Gigafire");
		public static const GottaOpenGift:StatusEffectType = mk("Gotta Open Gift");
		public static const HolliBurning:StatusEffectType = mk("Holli Burning");
		public static const Illusion:StatusEffectType = mk("Illusion");
		public static const ImpSkip:StatusEffectType = mk("ImpSkip");
		public static const ImpUber:StatusEffectType = mk("ImpUber");
		public static const JojoIsAssisting:StatusEffectType = mk("Jojo Is Assisting");
		public static const JojoPyre:StatusEffectType = mk("Jojo Pyre");
		public static const Keen:StatusEffectType = mk("keen");
		public static const Level:StatusEffectType = mk("level");
		public static const KitsuneFight:StatusEffectType = mk("Kitsune Fight");
		public static const LethicesRapeTentacles:StatusEffectType = mk("Lethices Rape Tentacles");
		public static const LustAura:StatusEffectType = mk("Lust Aura");
		public static const LustStick:StatusEffectType = mk("LustStick");
		public static const Milk:StatusEffectType = mk("milk");
		public static const MilkyUrta:StatusEffectType = mk("Milky Urta");
		public static const MinoMilk:StatusEffectType = mk("Mino Milk");
		public static const MinotaurEntangled:StatusEffectType = mk("Minotaur Entangled");

		public static const MissFirstRound:StatusEffectType = mk("miss first round");
		public static const NoLoot:StatusEffectType = mk("No Loot");
		public static const OnFire:StatusEffectType = mk("On Fire");
		public static const PCTailTangle:StatusEffectType = mk("PCTailTangle");
		public static const PeachLootLoss:StatusEffectType = mk("Peach Loot Loss");

		// @aimozg i don't know and do not fucking care if these two should be merged
		public static const PhyllaFight:StatusEffectType = mk("PhyllaFight");
		public static const phyllafight:StatusEffectType = mk("phyllafight");
		public static const Platoon:StatusEffectType = mk("platoon");
		public static const QueenBind:StatusEffectType = mk("QueenBind");
		// @aimozg HA HA HA
		public static const GiantBoulder:StatusEffectType = mk("Giant Boulder");
		public static const Round:StatusEffectType = mk("Round");
		public static const round:StatusEffectType = mk("round");
		public static const RunDisabled:StatusEffectType = mk("Run Disabled");
		public static const Shell:StatusEffectType = mk("Shell");
		public static const SirenSong:StatusEffectType = mk("Siren Song");
		public static const Spar:StatusEffectType = mk("spar");
		public static const Sparring:StatusEffectType = mk("sparring");
		public static const spiderfight:StatusEffectType = mk("spiderfight");
		public static const StunCooldown:StatusEffectType = mk("Stun Cooldown");
		public static const TentacleCoolDown:StatusEffectType = mk("TentacleCoolDown");
		public static const Timer:StatusEffectType = mk("Timer");
		public static const TimesBashed:StatusEffectType = mk("TimesBashed");
		public static const Uber:StatusEffectType = mk("Uber");
		public static const UrtaSecondWinded:StatusEffectType = mk("Urta Second Winded");
		public static const UsedTitsmother:StatusEffectType = mk("UsedTitsmother");
		public static const Vala:StatusEffectType = mk("vala");
		public static const Vapula:StatusEffectType = mk("Vapula");
		public static const WhipReady:StatusEffectType = mk("Whip Ready");

		//Plantgirl
		public static const happy:StatusEffectType = mk("happy");
		public static const horny:StatusEffectType = mk("horny");
		public static const grouchy:StatusEffectType = mk("grouchy");

		// combat
		public static const AcidSlap:CombatStatusEffect = mk2("Acid Slap");
		public static const AkbalSpeed:CombatStatusEffect = mk2("Akbal Speed");
		public static const AmilyVenom:CombatStatusEffect = mk2("Amily Venom");
		public static const AnemoneVenom:CombatStatusEffect = mk2("Anemone Venom");
		public static const AttackDisabled:CombatStatusEffect = mk2("Attack Disabled");
		public static const BasiliskCompulsion:CombatStatusEffect = mk2("Basilisk Compulsion");
		public static const BasiliskSlow:CombatStatusEffect = mk2("BasiliskSlow");
		public static const Berzerking:CombatStatusEffect = mk2("Berzerking");
		public static const Blind:CombatStatusEffect = mk2("Blind");
		public static const Bound:CombatStatusEffect = mk2("Bound");
		public static const CalledShot:CombatStatusEffect = mk2("Called Shot");
		public static const ChargeWeapon:CombatStatusEffect = mk2("Charge Weapon");
		public static const Chokeslam:CombatStatusEffect = mk2("Chokeslam");
		public static const Confusion:CombatStatusEffect = mk2("Confusion");
		public static const DemonSeed:CombatStatusEffect = mk2("DemonSeed");
		public static const Disarmed:CombatStatusEffect = mk2("Disarmed");
		public static const DriderKiss:CombatStatusEffect = mk2("Drider Kiss");

		public static const FirstAttack:CombatStatusEffect = mk2("FirstAttack");
		public static const GiantGrabbed:CombatStatusEffect = mk2("Giant Grabbed");
		public static const GiantStrLoss:CombatStatusEffect = mk2("GiantStrLoss");
		public static const GnollSpear:CombatStatusEffect = mk2("Gnoll Spear");
		public static const GooArmorBind:CombatStatusEffect = mk2("GooArmorBind");
		public static const GooArmorSilence:CombatStatusEffect = mk2("GooArmorSilence");
		public static const GooBind:CombatStatusEffect = mk2("GooBind");
		public static const HarpyBind:CombatStatusEffect = mk2("HarpyBind");
		public static const HolliConstrict:CombatStatusEffect = mk2("Holli Constrict");
		public static const InfestAttempted:CombatStatusEffect = mk2("infestAttempted");
		public static const IsabellaStunned:CombatStatusEffect = mk2("Isabella Stunned");
		public static const IzmaBleed:CombatStatusEffect = mk2("Izma Bleed");
		public static const KissOfDeath:CombatStatusEffect = mk2("Kiss of Death");
		public static const LizanBlowpipe:CombatStatusEffect = mk2("Lizan Blowpipe");
		public static const LustStones:CombatStatusEffect = mk2("lust stones");
		public static const lustvenom:CombatStatusEffect = mk2("lust venom");
		public static const Lustzerking:CombatStatusEffect = mk2("Lustzerking");
		public static const Might:CombatStatusEffect = mk2("Might");
		public static const NagaBind:CombatStatusEffect = mk2("Naga Bind");
		public static const NagaVenom:CombatStatusEffect = mk2("Naga Venom");
		public static const NoFlee:CombatStatusEffect = mk2("NoFlee");
		public static const ParalyzeVenom:CombatStatusEffect = mk2("paralyze venom");
		public static const PhysicalDisabled:CombatStatusEffect = mk2("Physical Disabled");
		public static const Poison:CombatStatusEffect = mk2("Poison");
		public static const Sandstorm:CombatStatusEffect = mk2("sandstorm");
		public static const Sealed:CombatStatusEffect = mk2("Sealed");
		public static const SheilaOil:CombatStatusEffect = mk2("Sheila Oil");
		public static const Shielding:CombatStatusEffect = mk2("Sheilding");
		public static const StoneLust:CombatStatusEffect = mk2("Stone Lust");
		public static const Stunned:CombatStatusEffect = mk2("Stunned");
		public static const TailWhip:CombatStatusEffect = mk2("Tail Whip");
		public static const TemporaryHeat:CombatStatusEffect = mk2("Temporary Heat");
		public static const TentacleBind:CombatStatusEffect = mk2("TentacleBind");
		public static const ThroatPunch:CombatStatusEffect = mk2("Throat Punch");
		public static const Titsmother:CombatStatusEffect = mk2("Titsmother");
		public static const TwuWuv:CombatStatusEffect = mk2("Twu Wuv");
		public static const UBERWEB:CombatStatusEffect = mk2("UBERWEB");
		public static const VolcanicFistProblem:CombatStatusEffect = mk2("Golem stuck its fist in the ground.");
		public static const VolcanicFrenzy:CombatStatusEffect = mk2("Golem is pissed off.");
		public static const VolcanicArmorRed:CombatStatusEffect = mk2("Armor temporarily reduced");
	    public static const VolcanicWeapRed:CombatStatusEffect = mk2("Weapon damage temporarily reduced");
		public static const Web:CombatStatusEffect = mk2("Web");
		public static const WebSilence:CombatStatusEffect = mk2("Web-Silence");
		public static const Whispered:CombatStatusEffect = mk2("Whispered");

		public static const RemovedArmor:CombatStatusEffect = mk2("Removed Armor");
		public static const JCLustLevel:CombatStatusEffect = mk2("JC Lust Level");
		public static const MirroredAttack:CombatStatusEffect = mk2("Mirrored Attack");
		public static const KnockedBack:CombatStatusEffect = mk2("Knocked Back");
		public static const Tentagrappled:CombatStatusEffect = mk2("Tentagrappled");
		public static const TentagrappleCooldown:CombatStatusEffect = mk2("Tentagrapple Cooldown");
		public static const ShowerDotEffect:CombatStatusEffect = mk2("Shower Dot Effect");
		public static const GardenerSapSpeed:CombatStatusEffect = mk2("Sap Speed");
		public static const VineHealUsed:CombatStatusEffect = mk2("Vine Heal Used");

		public static const DriderIncubusVenom:CombatStatusEffect = mk2("Drider Incubus Venom");
		public static const PurpleHaze:StatusEffectType = mk("PurpleHaze");
		public static const TaintedMind:StatusEffectType = mk("Tainted Mind");
		public static const MinotaurKingMusk:StatusEffectType = mk("Minotaur King Musk");
		public static const MinotaurKingsTouch:StatusEffectType = mk("Minotaur Kings Touch");
		public static const PigbysHands:StatusEffectType = mk("Pigbys Hands");
		public static const WhipSilence:CombatStatusEffect = mk2("Whip-Silence");

		/**
		 * Creates non-combat status affect
		 */
		private static function mk(id:String):StatusEffectType
		{
			return new StatusEffectType(id);
		}

		/**
		 * Creates combat status affect
		 */
		private static function mk2(id:String):CombatStatusEffect
		{
			return new CombatStatusEffect(id);
		}
	}
}


code:
/**
 * Created by aimozg on 31.01.14.
 */
package classes.StatusEffects
{
	import classes.StatusEffectType;

	public class CombatStatusEffect extends StatusEffectType
	{

		public function CombatStatusEffect(id:String)
		{
			super(id);
		}
	}
}


code:
package classes
{
	//Call CoC.timeAwareClassAdd if you want a class that implements this interface to receive time changes
	public interface TimeAwareInterface
	{
		/*	Called for every Class in the _timeAwareClassList each time the game time advances.
			Should be used for code with no screen output and short text output which can be bundled with
			other game text. Larger scenes which require an immediate pause should go in timeChangeLarge instead.
			Returning true indicates that you want the game to pause and display a set of screen output.
			Returning false indicates the function has produced no screen output.

			Note that all timeChanges are called first. All their text (if any) is displayed on one screen.
			Then, afterward, each timeChangeLarge is called and stops immediately if there is any screen output.
			Once the player presses [Next] the code will continue and display the next screen of text or
			(once all time changes are complete) finally get to the next screen of the game */
		function timeChange():Boolean;

		/*	Called for every Class in the _timeAwareClassList each time the game time advances.
			Should be used only for large scenes that need their own next button before proceeding with
			other time based events. This function is always called after the timeChange function and
			may be called multiple times on a single tick of the hour, so updates should go in timeChange()
			and any scene that triggers on timeChangeLarge must make sure it cannot be triggered twice.
			Returning true indicates that you want the game to pause and display your screen output.
			When this function returns true it is responsible for calling doNext, menu, choices, etc.
			Returning false indicates the function has produced no screen output. */
		function timeChangeLarge():Boolean;

	}
}


code:
package classes
{
	import classes.internals.Utils;

	public class VaginaClass
	{
		//constructor
		public function VaginaClass(vaginalWetness:Number = 1, vaginalLooseness:Number = 0, virgin:Boolean = false)
		{
			this.virgin=virgin;
			this.vaginalWetness=vaginalWetness;
			this.vaginalLooseness=vaginalLooseness;
		}
		//data
		//Vag wetness
		public var vaginalWetness:Number = 1;
		/*Vag looseness
		0 - virgin
		1 - normal
		2 - loose
		3 - very loose
		4 - gaping
		5 - monstrous*/
		public var vaginalLooseness:Number = 0;
		//Type
		//0 - Normal
		//5 - Black bugvag
		public var type:int = 0;
		public var virgin:Boolean = true;
		//Used during sex to determine how full it currently is.  For multi-dick sex.
		public var fullness:Number = 0;
		public var labiaPierced:Number = 0;
		public var labiaPShort:String = "";
		public var labiaPLong:String = "";
		public var clitPierced:Number = 0;
		public var clitPShort:String = "";
		public var clitPLong:String = "";

		public function validate():String
		{
			var error:String = "";
			error += Utils.validateNonNegativeNumberFields(this, "VaginaClass.validate", [
				"vaginalWetness", "vaginalLooseness", "type",
				"fullness", "labiaPierced", "clitPierced"
			]);
			if (labiaPierced) {
				if (labiaPShort == "") error += "Labia pierced but labiaPShort = ''. ";
				if (labiaPLong == "") error += "Labia pierced but labiaPLong = ''. ";
			} else {
				if (labiaPShort != "") error += "Labia not pierced but labiaPShort = '" + labiaPShort + "'. ";
				if (labiaPLong != "") error += "Labia not pierced but labiaPLong = '" + labiaPShort + "'. ";
			}
			if (clitPierced) {
				if (clitPShort == "") error += "Clit pierced but labiaPShort = ''. ";
				if (clitPLong == "") error += "Clit pierced but labiaPLong = ''. ";
			} else {
				if (clitPShort != "") error += "Clit not pierced but labiaPShort = '" + labiaPShort + "'. ";
				if (clitPLong != "") error += "Clit not pierced but labiaPLong = '" + labiaPShort + "'. ";
			}
			return error;
		}

		public function wetnessFactor():Number {
			if (vaginalWetness == 0) return 1.25;
			if (vaginalWetness == 1) return 1;
			if (vaginalWetness == 2) return 0.8;
			if (vaginalWetness == 3) return 0.7;
			if (vaginalWetness == 4) return 0.6;
			if (vaginalWetness == 5) return 0.5;
			return .5;
		}
		public function capacity():Number {
			if (vaginalLooseness == 0) return 8;
			if (vaginalLooseness == 1) return 16;
			if (vaginalLooseness == 2) return 24;
			if (vaginalLooseness == 3) return 36;
			if (vaginalLooseness == 4) return 56;
			if (vaginalLooseness == 5) return 100;
			return 10000;
		}
	}
}


code:
package classes.content
{
	import classes.BaseContent;
	/**
	 * ...
	 * @author Gedan
	 */
	public class TestContent extends BaseContent
	{

		public function TestContent()
		{

		}

		public function cheatSheet():void
		{
			clearOutput();

			outputText("<b>Parser Cheet Sheet:</b>\n\n");
			outputText("Descriptor (descriptor.as) Functions:\n");

			outputText("\nsackDescript " + player.sackDescript());
			outputText("\ncockClit " + player.cockClit());
//			outputText("\nballs " + balls(0, 0));
			outputText("\nsheathDesc " + player.sheathDesc());
			outputText("\nchestDesc " + player.chestDesc());
			outputText("\nallChestDesc " + player.allChestDesc());
			outputText("\nsMultiCockDesc " + player.sMultiCockDesc());
			outputText("\nSMultiCockDesc " + player.SMultiCockDesc());
			outputText("\noMultiCockDesc " + player.oMultiCockDesc());
			outputText("\nOMultiCockDesc " + player.OMultiCockDesc());
			outputText("\ntongueDescript " + player.tongueDescript());
			outputText("\nballsDescriptLight false " + player.ballsDescriptLight(false));
			outputText("\nballsDescriptLight true " + player.ballsDescriptLight(true));
			outputText("\nballDescript " + player.ballDescript());
			outputText("\nballsDescript " + player.ballsDescript());
			outputText("\nsimpleBallsDescript " + player.simpleBallsDescript());
			outputText("\nassholeDescript " + player.assholeDescript());
			outputText("\nhipDescript " + player.hipDescript());
			outputText("\nassDescript " + player.assDescript());
			outputText("\nbuttDescript " + player.buttDescript());
			outputText("\nnippleDescript " + player.nippleDescript(0));
			outputText("\nhairDescript " + player.hairDescript());
			outputText("\nhairOrFur " + player.hairOrFur());
			outputText("\nclitDescript " + player.clitDescript());
			outputText("\nvaginaDescript " + player.vaginaDescript());
			outputText("\nallVaginaDescript " + player.allVaginaDescript());
			outputText("\nmultiCockDescriptLight " + player.multiCockDescriptLight());
			outputText("\ncockAdjective " + player.cockAdjective());
			outputText("\ncockDescript " + player.cockDescript(0));
			outputText("\nbiggestBreastSizeDescript " + biggestBreastSizeDescript());
			outputText("\nbreaseSize 5" + breastSize(5));
			outputText("\nbreastDescript " + player.breastDescript(0));
			outputText("\ncockHead " + player.cockHead());
			outputText("\nbreastCup 5 " + breastCup(5));

			outputText("\n\nParser Tags (Single)L\n");
			outputText("\naagility [agility]");
			outputText("\narmor [armor]");
			outputText("\narmorname [armorname]");
			outputText("\nass [ass]");
			outputText("\nasshole [asshole]");
			outputText("\nballs [balls]");
			outputText("\nboyfriend [boyfriend]");
			outputText("\nbutt [butt]");
			outputText("\nbutthole [butthole]");
			outputText("\nchest [chest]");
			outputText("\nclit [clit]");
			outputText("\ncock [cock]");
			outputText("\ncockhead [cockhead]");
			outputText("\ncocks [cocks]");
			outputText("\ncunt [cunt]");
			outputText("\neachcock [eachCock]");
			outputText("\nevade [evade]");
			outputText("\nface [face]");
			outputText("\nfeet [feet]");
			outputText("\nfoot [foot]");
			outputText("\nfullchest [fullchest]");
			outputText("\nhair [hair]");
			outputText("\nhairorfur [hairorfur]");
			outputText("\nhe [he]");
			outputText("\nhim [him]");
			outputText("\nhips [hips]");
			outputText("\nhis [his]");
			outputText("\nleg [leg]");
			outputText("\nlegs [legs]");
			outputText("\nman [man]");
			outputText("\nmaster [master]");
			outputText("\nmisdirection [misdirection]");
			outputText("\nmulticockdescriptlight [multicockdescriptlight]");
			outputText("\nname [name]");
			outputText("\nnipple [nipple]");
			outputText("\nnipples [nipples]");
			outputText("\nonecock [onecock]");
			outputText("\npg [pg]");
			outputText("\npussy [pussy]");
			outputText("\nsack [sack]");
			outputText("\nsheath [sheath]");
			outputText("\nskin [skin]");
			outputText("\nskinfurscales [skinfurscales]");
			outputText("\ntongue [tongue]");
			outputText("\nvag [vag]");
			outputText("\nvagina [vagina]");
			outputText("\nvagorass [vagorass]");
			outputText("\nweapon [weapon]");
			outputText("\nweaponname [weaponname]");

			trace("Spammed!");
			doNext(camp.returnToCampUseOneHour);
		}

	}

}