diff --git a/code/__DEFINES/traits.dm b/code/__DEFINES/traits.dm index 4b8a66423d..2cba494ed8 100644 --- a/code/__DEFINES/traits.dm +++ b/code/__DEFINES/traits.dm @@ -163,6 +163,8 @@ #define TRAIT_MUSICIAN "musician" #define TRAIT_PERMABONER "permanent_arousal" #define TRAIT_NEVERBONER "never_aroused" +#define TRAIT_NYMPHO "nymphomania" +#define TRAIT_MASO "masochism" #define TRAIT_HIGH_BLOOD "high_blood" #define TRAIT_PARA "paraplegic" #define TRAIT_EMPATH "empath" diff --git a/code/datums/traits/neutral.dm b/code/datums/traits/neutral.dm index a241da9be8..ab2a69e7e9 100644 --- a/code/datums/traits/neutral.dm +++ b/code/datums/traits/neutral.dm @@ -88,6 +88,22 @@ if(quirk_holder) quirk_holder.remove_client_colour(/datum/client_colour/monochrome) +/datum/quirk/libido + name = "Nymphomania" + desc = "You're always feeling a bit in heat. Also, you get aroused faster than usual." + value = 0 + mob_trait = TRAIT_PERMABONER + gain_text = "You are feeling extra wild." + lose_text = "You don't feel that burning sensation anymore." + +/datum/quirk/maso + name = "Masochism" + desc = "You are aroused by pain." + value = 0 + mob_trait = TRAIT_MASO + gain_text = "You desire to be hurt." + lose_text = "Pain has become less exciting for you." + /datum/quirk/alcohol_intolerance name = "Alcohol Intolerance" desc = "You take toxin damage from alcohol rather than getting drunk." diff --git a/code/modules/mob/living/carbon/human/species.dm b/code/modules/mob/living/carbon/human/species.dm index a8603a2a41..8a38f71076 100644 --- a/code/modules/mob/living/carbon/human/species.dm +++ b/code/modules/mob/living/carbon/human/species.dm @@ -1582,6 +1582,8 @@ GLOBAL_LIST_EMPTY(roundstart_race_names) ) user.do_attack_animation(target, ATTACK_EFFECT_FACE_SLAP) user.adjustStaminaLossBuffered(3) + if (!HAS_TRAIT(target, TRAIT_PERMABONER)) + stop_wagging_tail(target) return FALSE else if(aim_for_groin && (target == user || target.lying || same_dir) && (target_on_help || target_restrained || target_aiming_for_groin)) if(target.client?.prefs.cit_toggles & NO_ASS_SLAP) @@ -1589,6 +1591,11 @@ GLOBAL_LIST_EMPTY(roundstart_race_names) return FALSE user.do_attack_animation(target, ATTACK_EFFECT_ASS_SLAP) user.adjustStaminaLossBuffered(3) + target.adjust_arousal(20,maso = TRUE) + if (ishuman(target) && HAS_TRAIT(target, TRAIT_MASO) && target.has_dna() && prob(10)) + target.mob_climax(forced_climax=TRUE) + if (!HAS_TRAIT(target, TRAIT_PERMABONER)) + stop_wagging_tail(target) playsound(target.loc, 'sound/weapons/slap.ogg', 50, 1, -1) user.visible_message(\ "\The [user] slaps \the [target]'s ass!",\ @@ -1947,6 +1954,8 @@ GLOBAL_LIST_EMPTY(roundstart_race_names) if(BP) if(damage > 0 ? BP.receive_damage(damage_amount, 0) : BP.heal_damage(abs(damage_amount), 0)) H.update_damage_overlays() + if(HAS_TRAIT(H, TRAIT_MASO) && prob(damage_amount)) + H.mob_climax(forced_climax=TRUE) else//no bodypart, we deal damage with a more general method. H.adjustBruteLoss(damage_amount) diff --git a/code/modules/reagents/chemistry/reagents/drink_reagents.dm b/code/modules/reagents/chemistry/reagents/drink_reagents.dm index ba4fe4909e..5403da93b3 100644 --- a/code/modules/reagents/chemistry/reagents/drink_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/drink_reagents.dm @@ -966,14 +966,12 @@ M.emote("nya") if(prob(20)) to_chat(M, "[pick("Headpats feel nice.", "Backrubs would be nice.", "Mew")]") - if(M.client?.prefs.arousable && !(M.client?.prefs.cit_toggles & NO_APHRO) && prob(5)) - for(var/obj/item/organ/genital/G in M.internal_organs) - if(!G.aroused_state && prob(5*G.sensitivity)) - G.set_aroused_state(TRUE) - G.update_appearance() - if(G.aroused_state) - to_chat(M, "You feel like playing with your [G.name]!") - + if(ishuman(M)) + var/mob/living/carbon/human/H = M + var/list/adjusted = H.adjust_arousal(5,aphro = TRUE) + for(var/g in adjusted) + var/obj/item/organ/genital/G = g + to_chat(M, "You feel like playing with your [G.name]!") ..() /datum/reagent/consumable/monkey_energy diff --git a/code/modules/reagents/chemistry/reagents/other_reagents.dm b/code/modules/reagents/chemistry/reagents/other_reagents.dm index a39746519a..894e48f5c2 100644 --- a/code/modules/reagents/chemistry/reagents/other_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/other_reagents.dm @@ -2280,12 +2280,11 @@ M.emote("nya") if(prob(20)) to_chat(M, "[pick("Headpats feel nice.", "The feeling of a hairball...", "Backrubs would be nice.", "Whats behind those doors?")]") - if(M.client?.prefs.arousable && !(M.client?.prefs.cit_toggles & NO_APHRO && ishuman(M))) + if(ishuman(M)) var/mob/living/carbon/human/H = M - for(var/obj/item/organ/genital/G in H.internal_organs) - if(!G.aroused_state && prob(2*G.sensitivity)) - G.set_aroused_state(TRUE) - G.update_appearance() - if(G.aroused_state) - to_chat(M, "You feel like playing with your [G.name]!") + var/list/adjusted = H.adjust_arousal(2,aphro = TRUE) + for(var/g in adjusted) + var/obj/item/organ/genital/G = g + to_chat(M, "You feel like playing with your [G.name]!") + ..() diff --git a/code/modules/surgery/organs/vocal_cords.dm b/code/modules/surgery/organs/vocal_cords.dm index 7df7421c69..6dc1d1b6ce 100644 --- a/code/modules/surgery/organs/vocal_cords.dm +++ b/code/modules/surgery/organs/vocal_cords.dm @@ -822,6 +822,10 @@ continue if (E.lewd) addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "[E.enthrallGender] has praised me!!"), 5) + if(HAS_TRAIT(L, TRAIT_MASO)) + E.enthrallTally -= power_multiplier + E.resistanceTally += power_multiplier + E.cooldown += 1 else addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "I've been praised for doing a good job!"), 5) E.resistanceTally -= power_multiplier @@ -839,7 +843,16 @@ if(L == user) continue if (E.lewd) - addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "I've let [E.enthrallGender] down..."), 5) + if(HAS_TRAIT(L, TRAIT_MASO)) + if(ishuman(L)) + var/mob/living/carbon/human/H = L + H.adjust_arousal(3*power_multiplier,maso = TRUE) + descmessage += "And yet, it feels so good..!" //I don't really understand masco, is this the right sort of thing they like? + E.enthrallTally += power_multiplier + E.resistanceTally -= power_multiplier + addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "I've let [E.enthrallGender] down...!"), 5) + else + addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "I've let [E.enthrallGender] down..."), 5) else addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "I've failed [E.master]..."), 5) E.resistanceTally += power_multiplier diff --git a/modular_citadel/code/datums/status_effects/chems.dm b/modular_citadel/code/datums/status_effects/chems.dm index 4e43b6a8b7..fec807bef3 100644 --- a/modular_citadel/code/datums/status_effects/chems.dm +++ b/modular_citadel/code/datums/status_effects/chems.dm @@ -633,6 +633,9 @@ //Shocking truth! else if (lowertext(customTriggers[trigger]) == "shock") + if (lewd && ishuman(C)) + var/mob/living/carbon/human/H = C + H.adjust_arousal(5) C.jitteriness += 100 C.stuttering += 25 C.Knockdown(60) diff --git a/modular_citadel/code/modules/arousal/arousal.dm b/modular_citadel/code/modules/arousal/arousal.dm index 5f58121fd4..818c5c7b1e 100644 --- a/modular_citadel/code/modules/arousal/arousal.dm +++ b/modular_citadel/code/modules/arousal/arousal.dm @@ -41,6 +41,27 @@ update_body() + +/mob/living/carbon/human/proc/adjust_arousal(strength,aphro = FALSE,maso = FALSE) // returns all genitals that were adjust + var/list/obj/item/organ/genital/genit_list = list() + if(!client?.prefs.arousable || (aphro && (client?.prefs.cit_toggles & NO_APHRO)) || (maso && !HAS_TRAIT(src, TRAIT_MASO))) + return // no adjusting made here + if(strength>0) + for(var/obj/item/organ/genital/G in internal_organs) + if(!G.aroused_state && prob(strength*G.sensitivity)) + G.set_aroused_state(TRUE) + G.update_appearance() + if(G.aroused_state) + genit_list += G + else + for(var/obj/item/organ/genital/G in internal_organs) + if(G.aroused_state && prob(strength*G.sensitivity)) + G.set_aroused_state(FALSE) + G.update_appearance() + if(G.aroused_state) + genit_list += G + return genit_list + /obj/item/organ/genital/proc/climaxable(mob/living/carbon/human/H, silent = FALSE) //returns the fluid source (ergo reagents holder) if found. if(CHECK_BITFIELD(genital_flags, GENITAL_FUID_PRODUCTION)) . = reagents diff --git a/modular_citadel/code/modules/reagents/reagents/cit_reagents.dm b/modular_citadel/code/modules/reagents/reagents/cit_reagents.dm index 9ec1c8b010..cbe2591528 100644 --- a/modular_citadel/code/modules/reagents/reagents/cit_reagents.dm +++ b/modular_citadel/code/modules/reagents/reagents/cit_reagents.dm @@ -108,12 +108,10 @@ to_chat(M, "[aroused_message]") if(ishuman(M)) var/mob/living/carbon/human/H = M - for(var/obj/item/organ/genital/G in H.internal_organs) - if(!G.aroused_state && prob(current_cycle*G.sensitivity)) - G.set_aroused_state(TRUE) - G.update_appearance() - if(G.aroused_state) - to_chat(M, "[G.arousal_verb]!") + var/list/genits = H.adjust_arousal(current_cycle, aphro = TRUE) // redundant but should still be here + for(var/g in genits) + var/obj/item/organ/genital/G = g + to_chat(M, "[G.arousal_verb]!") ..() /datum/reagent/drug/aphrodisiacplus @@ -144,12 +142,10 @@ REMOVE_TRAIT(M,TRAIT_NEVERBONER,"aphro") if(ishuman(M)) var/mob/living/carbon/human/H = M - for(var/obj/item/organ/genital/G in H.internal_organs) - if(!G.aroused_state) - G.set_aroused_state(TRUE) - G.update_appearance() - if(G.aroused_state) - to_chat(M, "[G.arousal_verb]!") + var/list/genits = H.adjust_arousal(100, aphro = TRUE) // redundant but should still be here + for(var/g in genits) + var/obj/item/organ/genital/G = g + to_chat(M, "[G.arousal_verb]!") ..() /datum/reagent/drug/aphrodisiacplus/addiction_act_stage2(mob/living/M) @@ -169,9 +165,9 @@ /datum/reagent/drug/aphrodisiacplus/overdose_process(mob/living/M) if(M && M.client?.prefs.arousable && !(M.client?.prefs.cit_toggles & NO_APHRO) && prob(33)) if(prob(5) && ishuman(M) && M.has_dna() && (M.client?.prefs.cit_toggles & BIMBOFICATION)) - if(!HAS_TRAIT(M,TRAIT_PERMABONER)) //Less spam + if(!HAS_TRAIT(M,TRAIT_PERMABONER)) to_chat(M, "Your libido is going haywire!") - ADD_TRAIT(M,TRAIT_PERMABONER,"aphro") + ADD_TRAIT(M,TRAIT_PERMABONER,"aphro") ..() /datum/reagent/drug/anaphrodisiac @@ -187,14 +183,9 @@ /datum/reagent/drug/anaphrodisiac/on_mob_life(mob/living/M) if(M && M.client?.prefs.arousable && prob(16)) if(ishuman(M)) - var/unboner = FALSE var/mob/living/carbon/human/H = M - for(var/obj/item/organ/genital/G in H.internal_organs) - if(G.aroused_state) - G.set_aroused_state(FALSE) - G.update_appearance() - unboner = (G.aroused_state == FALSE) - if(unboner) + var/list/genits = H.adjust_arousal(-100, aphro = TRUE) + if(genits.len) to_chat(M, "You no longer feel aroused.") ..() @@ -211,19 +202,16 @@ if(M && M.client?.prefs.arousable) REMOVE_TRAIT(M,TRAIT_PERMABONER,"aphro") if(ishuman(M)) - var/unboner = FALSE var/mob/living/carbon/human/H = M - for(var/obj/item/organ/genital/G in H.internal_organs) - if(G.aroused_state) - G.set_aroused_state(FALSE) - G.update_appearance() - unboner = (G.aroused_state == FALSE) - if(unboner) + var/list/genits = H.adjust_arousal(-100, aphro = TRUE) + if(genits.len) to_chat(M, "You no longer feel aroused.") + ..() /datum/reagent/drug/anaphrodisiacplus/overdose_process(mob/living/M) if(M && M.client?.prefs.arousable && prob(5)) + to_chat(M, "You feel like you'll never feel aroused again...") ADD_TRAIT(M,TRAIT_NEVERBONER,"aphro") ..()