diff --git a/modular_ss220/species/serpentids/code/common/defines.dm b/modular_ss220/species/serpentids/code/common/defines.dm index 44ba95327c60..94921ef9d863 100644 --- a/modular_ss220/species/serpentids/code/common/defines.dm +++ b/modular_ss220/species/serpentids/code/common/defines.dm @@ -39,3 +39,11 @@ var/action_mult = 1 var/equipment_black_list = list() var/butt_sprite_icon = 'icons/obj/butts.dmi' + var/bio_chips = list() + +/datum/species/on_species_gain(mob/living/carbon/human/H) + .. () + if(bio_chips) + for(var/bio_chip_type in bio_chips) + var/obj/item/bio_chip/I = new bio_chip_type(H) + I.implant(H, null) diff --git a/modular_ss220/species/serpentids/code/common/serpentids.dm b/modular_ss220/species/serpentids/code/common/serpentids.dm index b91db48c2906..a39e0db40c0d 100644 --- a/modular_ss220/species/serpentids/code/common/serpentids.dm +++ b/modular_ss220/species/serpentids/code/common/serpentids.dm @@ -14,6 +14,7 @@ eyes = "serpentid_eyes_s" butt_sprite_icon = 'modular_ss220/species/serpentids/icons/mob/r_serpentid_butt.dmi' butt_sprite = "serpentid" + nojumpsuit = TRUE species_traits = list(LIPS, NO_HAIR) inherent_traits = list(TRAIT_CHUNKYFINGERS, TRAIT_RESISTHEAT, TRAIT_RESISTHIGHPRESSURE, TRAIT_RESISTLOWPRESSURE, TRAIT_NOPAIN) @@ -56,6 +57,8 @@ "chest" = /obj/item/organ/internal/cyberimp/chest/serpentid_blades, ) + bio_chips = list(/obj/item/bio_chip/tracking) + has_limbs = list( "chest" = list("path" = /obj/item/organ/external/chest/carapace, "descriptor" = "chest"), "groin" = list("path" = /obj/item/organ/external/groin/carapace, "descriptor" = "groin"), @@ -151,7 +154,7 @@ H.buckle_lying = buckle_lying H.update_transform() H.AddComponent(/datum/component/footstep, FOOTSTEP_MOB_SLIME, 1, -6) - H.AddComponent(/datum/component/mob_overlay_shift, shift_y_hand = 3, shift_y_belt = 7, shift_y_back = 7) //shift_xs_hand = 12 + H.AddComponent(/datum/component/mob_overlay_shift, shift_y_hand = 3, shift_xs_belt = 5, shift_y_belt = 7, shift_y_back = 7, shift_y_head = 10, shift_xs_head = 3) //shift_xs_hand = 12 H.AddComponent(/datum/component/gadom_living) H.AddComponent(/datum/component/gadom_cargo) H.verbs += /mob/living/carbon/human/proc/emote_gbsroar @@ -171,8 +174,9 @@ switch(slot) if(SLOT_HUD_SHOES) return FALSE - for(var/queip_type in equipment_black_list) - if(istype(I, queip_type)) + if(SLOT_HUD_JUMPSUIT) + return FALSE + if(SLOT_HUD_OUTER_SUIT) return FALSE . = .. () diff --git a/modular_ss220/species/serpentids/code/components/mob_overlay_shift.dm b/modular_ss220/species/serpentids/code/components/mob_overlay_shift.dm index 4e6c77e857fd..fdcaad21b3cd 100644 --- a/modular_ss220/species/serpentids/code/components/mob_overlay_shift.dm +++ b/modular_ss220/species/serpentids/code/components/mob_overlay_shift.dm @@ -10,6 +10,8 @@ #define MOB_OVERLAY_SHIFT_CHECK (1<<0) /datum/component/mob_overlay_shift + var/dir = 1 + var/mob/living/carbon/human/mob var/shift_x_inhand = 0 var/shift_x_center_inhand = 0 @@ -38,7 +40,16 @@ var/shift_x_front_back = 0 var/shift_y_front_back = 0 -/datum/component/mob_overlay_shift/Initialize(caller_mob, shift_xs_hand = 0, shift_ys_hand = 0, shift_xf_hand = 0, shift_yf_hand = 0, shift_x_hand = 0, shift_y_hand = 0, shift_xs_belt = 0, shift_ys_belt = 0, shift_xf_belt = 0, shift_yf_belt = 0, shift_x_belt = 0, shift_y_belt = 0, shift_xs_back = 0, shift_ys_back = 0, shift_xf_back = 0, shift_yf_back = 0, shift_x_back = 0, shift_y_back = 0) + var/shift_x_head = 0 + var/shift_x_center_head = 0 + var/shift_y_head = 0 + var/shift_y_center_head = 0 + var/shift_x_side_head = 0 + var/shift_y_side_head = 0 + var/shift_x_front_head = 0 + var/shift_y_front_head = 0 + +/datum/component/mob_overlay_shift/Initialize(caller_mob, shift_xs_hand = 0, shift_ys_hand = 0, shift_xf_hand = 0, shift_yf_hand = 0, shift_x_hand = 0, shift_y_hand = 0, shift_xs_belt = 0, shift_ys_belt = 0, shift_xf_belt = 0, shift_yf_belt = 0, shift_x_belt = 0, shift_y_belt = 0, shift_xs_back = 0, shift_ys_back = 0, shift_xf_back = 0, shift_yf_back = 0, shift_x_back = 0, shift_y_back = 0, shift_xs_head = 0, shift_ys_head = 0, shift_xf_head = 0, shift_yf_head = 0, shift_x_head = 0, shift_y_head = 0) ..() mob = parent @@ -63,6 +74,13 @@ shift_x_front_back = shift_xf_back shift_y_front_back = shift_yf_back + shift_x_center_head = shift_x_head + shift_y_center_head = shift_y_head + shift_x_side_head = shift_xs_head + shift_y_side_head = shift_ys_head + shift_x_front_head = shift_xf_head + shift_y_front_head = shift_yf_head + /datum/component/mob_overlay_shift/RegisterWithParent() RegisterSignal(parent, COMSIG_MOB_OVERLAY_SHIFT_CALL, PROC_REF(shift_call)) RegisterSignal(parent, COMSIG_MOB_OVERLAY_SHIFT_CHECK, PROC_REF(module_available)) @@ -79,7 +97,9 @@ //Проки, срабатываемые при получении или исцелении урона /datum/component/mob_overlay_shift/proc/shift_call(mob, new_dir) - switch(new_dir) + if (new_dir) + dir = new_dir + switch(dir) if(EAST) shift_x_inhand = shift_x_side_inhand + shift_x_center_inhand shift_y_inhand = shift_y_side_inhand + shift_y_center_inhand @@ -87,6 +107,8 @@ shift_y_belt = shift_y_side_belt + shift_y_center_belt shift_x_back = shift_x_side_back + shift_x_center_back shift_y_back = shift_y_side_back + shift_y_center_back + shift_x_head = shift_x_side_head + shift_x_center_head + shift_y_head = shift_y_side_head + shift_y_center_head if(WEST) shift_x_inhand = -shift_x_side_inhand + shift_x_center_inhand shift_y_inhand = -shift_y_side_inhand + shift_y_center_inhand @@ -94,6 +116,8 @@ shift_y_belt = -shift_y_side_belt + shift_y_center_belt shift_x_back = -shift_x_side_back + shift_x_center_back shift_y_back = -shift_y_side_back + shift_y_center_back + shift_x_head = -shift_x_side_head + shift_x_center_head + shift_y_head = -shift_y_side_head + shift_y_center_head if(NORTH) shift_x_inhand = shift_x_front_inhand + shift_x_center_inhand shift_y_inhand = shift_y_front_inhand + shift_y_center_inhand @@ -101,6 +125,8 @@ shift_y_belt = shift_y_front_belt + shift_y_center_belt shift_x_back = shift_x_front_back + shift_x_center_back shift_y_back = shift_y_front_back + shift_y_center_back + shift_x_head = shift_x_front_head + shift_x_center_head + shift_y_head = shift_y_front_head + shift_y_center_head if(SOUTH) shift_x_inhand = -shift_x_front_inhand + shift_x_center_inhand shift_y_inhand = -shift_y_front_inhand + shift_y_center_inhand @@ -108,6 +134,8 @@ shift_y_belt = -shift_y_front_belt + shift_y_center_belt shift_x_back = -shift_x_front_back + shift_x_center_back shift_y_back = -shift_y_front_back + shift_y_center_back + shift_x_head = -shift_x_front_head + shift_x_center_head + shift_y_head = -shift_y_front_head + shift_y_center_head update_call() /datum/component/mob_overlay_shift/proc/update_call() @@ -115,6 +143,9 @@ update_inv_l_hand() update_inv_belt() update_inv_back() + update_inv_head() + update_inv_glasses() + update_inv_ears() /datum/component/mob_overlay_shift/proc/update_inv_belt() mob.remove_overlay(BELT_LAYER) @@ -226,7 +257,132 @@ mob.overlays_standing[L_HAND_LAYER] = standing mob.apply_overlay(L_HAND_LAYER) +/datum/component/mob_overlay_shift/proc/update_inv_head() + mob.remove_overlay(HEAD_LAYER) + if(mob.client && mob.hud_used) + var/atom/movable/screen/inventory/inv = mob.hud_used.inv_slots[SLOT_HUD_HEAD] + if(inv) + inv.update_icon() + + if(mob.head) + mob.update_hud_head(mob.head) + var/mutable_appearance/standing + if(mob.head.sprite_sheets && mob.head.sprite_sheets[mob.dna.species.sprite_sheet_name]) + standing = mutable_appearance(mob.head.sprite_sheets[mob.dna.species.sprite_sheet_name], "[mob.head.icon_state]", layer = -HEAD_LAYER) + if(istype(mob.head, /obj/item/clothing/head/helmet/space/plasmaman)) + var/obj/item/clothing/head/helmet/space/plasmaman/P = mob.head + if(!P.up) + standing.overlays += P.visor_icon + else if(mob.head.icon_override) + standing = mutable_appearance(mob.head.icon_override, "[mob.head.icon_state]", layer = -HEAD_LAYER) + else + standing = mutable_appearance('icons/mob/clothing/head.dmi', "[mob.head.icon_state]", layer = -HEAD_LAYER) + + if(mob.head.blood_DNA) + var/image/bloodsies = image("icon" = mob.dna.species.blood_mask, "icon_state" = "helmetblood") + bloodsies.color = mob.head.blood_color + standing.overlays += bloodsies + standing.alpha = mob.head.alpha + standing.color = mob.head.color + standing.pixel_x = shift_x_head + standing.pixel_y = shift_y_head + mob.overlays_standing[HEAD_LAYER] = standing + mob.apply_overlay(HEAD_LAYER) + +/datum/component/mob_overlay_shift/proc/update_inv_glasses() + mob.remove_overlay(GLASSES_LAYER) + mob.remove_overlay(GLASSES_OVER_LAYER) + mob.remove_overlay(OVER_MASK_LAYER) + + if(mob.client && mob.hud_used) + var/atom/movable/screen/inventory/inv = mob.hud_used.inv_slots[SLOT_HUD_GLASSES] + if(inv) + inv.update_icon() + + if(mob.glasses) + var/mutable_appearance/new_glasses + var/obj/item/organ/external/head/head_organ = mob.get_organ("head") + mob.update_hud_glasses(mob.glasses) + + if(mob.glasses.icon_override) + new_glasses = mutable_appearance(mob.glasses.icon_override, "[mob.glasses.icon_state]", layer = -GLASSES_LAYER) + else if(mob.glasses.sprite_sheets && mob.glasses.sprite_sheets[head_organ.dna.species.sprite_sheet_name]) + new_glasses = mutable_appearance(mob.glasses.sprite_sheets[head_organ.dna.species.sprite_sheet_name], "[mob.glasses.icon_state]", layer = -GLASSES_LAYER) + else + new_glasses = mutable_appearance('icons/mob/clothing/eyes.dmi', "[mob.glasses.icon_state]", layer = -GLASSES_LAYER) + + new_glasses.pixel_x = shift_x_head + new_glasses.pixel_y = shift_y_head + + var/datum/sprite_accessory/hair/hair_style = GLOB.hair_styles_full_list[head_organ.h_style] + var/obj/item/clothing/glasses/G = mob.glasses + if(istype(G) && G.over_mask) //If the user's used the 'wear over mask' verb on the glasses. + new_glasses.layer = -OVER_MASK_LAYER + mob.overlays_standing[OVER_MASK_LAYER] = new_glasses + mob.apply_overlay(OVER_MASK_LAYER) + else if(hair_style && hair_style.glasses_over) //Select which layer to use based on the properties of the hair style. Hair styles with hair that don't overhang the arms of the glasses should have glasses_over set to a positive value. + new_glasses.layer = -GLASSES_OVER_LAYER + mob.overlays_standing[GLASSES_OVER_LAYER] = new_glasses + mob.apply_overlay(GLASSES_OVER_LAYER) + else + mob.overlays_standing[GLASSES_LAYER] = new_glasses + mob.apply_overlay(GLASSES_LAYER) + + mob.update_misc_effects() + +/datum/component/mob_overlay_shift/proc/update_inv_ears() + mob.remove_overlay(LEFT_EAR_LAYER) + mob.remove_overlay(RIGHT_EAR_LAYER) + + if(mob.client && mob.hud_used) + var/atom/movable/screen/inventory/left_ear_inv = mob.hud_used.inv_slots[SLOT_HUD_LEFT_EAR] + var/atom/movable/screen/inventory/right_ear_inv = mob.hud_used.inv_slots[SLOT_HUD_RIGHT_EAR] + if(left_ear_inv) + left_ear_inv.update_icon() + if(right_ear_inv) + right_ear_inv.update_icon() + + if(mob.l_ear) + mob.update_hud_l_ear(mob.l_ear) + + var/left_ear_item_state = mob.l_ear.item_state ? mob.l_ear.item_state : mob.l_ear.icon_state + var/left_ear_icon = 'icons/mob/clothing/ears.dmi' + if(mob.l_ear.sprite_sheets && mob.l_ear.sprite_sheets[mob.dna.species.sprite_sheet_name]) + left_ear_icon = mob.l_ear.sprite_sheets[mob.dna.species.sprite_sheet_name] + if(mob.l_ear.icon_override) + left_ear_item_state = "[left_ear_item_state]_l" + left_ear_icon = mob.l_ear.icon_override + + var/mutable_appearance/standing = mutable_appearance(left_ear_icon, left_ear_item_state, layer = -LEFT_EAR_LAYER) + standing.pixel_x = shift_x_head + standing.pixel_y = shift_y_head + mob.overlays_standing[LEFT_EAR_LAYER] = standing + + if(mob.r_ear) + mob.update_hud_r_ear(mob.r_ear) + + var/right_ear_item_state = mob.r_ear.item_state ? mob.r_ear.item_state : mob.r_ear.icon_state + var/right_ear_icon = 'icons/mob/clothing/ears.dmi' + if(mob.r_ear.sprite_sheets && mob.r_ear.sprite_sheets[mob.dna.species.sprite_sheet_name]) + right_ear_icon = mob.r_ear.sprite_sheets[mob.dna.species.sprite_sheet_name] + if(mob.r_ear.icon_override) + right_ear_icon = "[right_ear_item_state]_l" + right_ear_icon = mob.r_ear.icon_override + + var/mutable_appearance/standing = mutable_appearance(right_ear_icon, right_ear_item_state, layer = -RIGHT_EAR_LAYER) + standing.pixel_x = shift_x_head + standing.pixel_y = shift_y_head + mob.overlays_standing[RIGHT_EAR_LAYER] = standing + + mob.apply_overlay(LEFT_EAR_LAYER) + mob.apply_overlay(RIGHT_EAR_LAYER) + /mob/living/carbon/human/setDir(new_dir) . = ..() if(SEND_SIGNAL(src, COMSIG_MOB_OVERLAY_SHIFT_CHECK) & MOB_OVERLAY_SHIFT_CHECK) SEND_SIGNAL(src, COMSIG_MOB_OVERLAY_SHIFT_CALL, new_dir) + +/mob/living/carbon/human/Life(seconds, times_fired) + . = ..() + if(SEND_SIGNAL(src, COMSIG_MOB_OVERLAY_SHIFT_CHECK) & MOB_OVERLAY_SHIFT_CHECK) + SEND_SIGNAL(src, COMSIG_MOB_OVERLAY_SHIFT_CALL) diff --git a/modular_ss220/species/serpentids/code/update_icons.dm b/modular_ss220/species/serpentids/code/update_icons.dm index ad093c5d1388..56bb0d78ef72 100644 --- a/modular_ss220/species/serpentids/code/update_icons.dm +++ b/modular_ss220/species/serpentids/code/update_icons.dm @@ -1,18 +1,70 @@ //Обновление иконок для кастомных рас /datum/character_save/update_preview_icon(for_observer=0) . = .. () + //Это ужасно,но так можно кастомным расам выдавать кастомные глаза (я хз, почему сработало так, нужны разьяснения) var/datum/species/selected_specie = GLOB.all_species[species] + if (istype(selected_specie, /datum/species/serpentid)) + qdel(preview_icon_front) + qdel(preview_icon_side) + qdel(preview_icon) - //Это ужасно,но так можно кастомным расам выдавать кастомные глаза (я хз, почему сработало так, нужны разьяснения) - var/icon/face_s = new/icon("icon" = selected_specie.eyes_icon, "icon_state" = selected_specie.eyes) - if(!(selected_specie.bodyflags & NO_EYES)) - var/icon/eyes_s = new/icon("icon" = selected_specie.eyes_icon, "icon_state" = selected_specie ? selected_specie.eyes : "eyes_s") - eyes_s.Blend(e_colour, ICON_ADD) - face_s.Blend(eyes_s, ICON_OVERLAY) - - preview_icon.Blend(face_s, ICON_OVERLAY) - preview_icon_front = new(preview_icon, dir = SOUTH) - preview_icon_side = new(preview_icon, dir = WEST) + var/g = "m" + if(body_type == FEMALE) + g = "f" + + var/icon/icobase + if(selected_specie.bodyflags & HAS_ICON_SKIN_TONE) //Handling species-specific icon-based skin tones by flagged race. + var/mob/living/carbon/human/H = new + H.dna.species = selected_specie + H.s_tone = s_tone + H.dna.species.updatespeciescolor(H, 0) //The mob's species wasn't set, so it's almost certainly different than the character's species at the moment. Thus, we need to be owner-insensitive. + var/obj/item/organ/external/chest/C = H.get_organ("chest") + icobase = C.icobase ? C.icobase : C.dna.species.icobase + qdel(H) + else + icobase = selected_specie.icobase + + preview_icon = new /icon(icobase, "torso_[g]") + preview_icon.Blend(new /icon(icobase, "groin_[g]"), ICON_OVERLAY) + var/head = "head" + if(alt_head && selected_specie.bodyflags & HAS_ALT_HEADS) + var/datum/sprite_accessory/alt_heads/H = GLOB.alt_heads_list[alt_head] + if(H.icon_state) + head = H.icon_state + preview_icon.Blend(new /icon(icobase, "[head]_[g]"), ICON_OVERLAY) + + for(var/name in list("chest", "groin", "head", "r_arm", "r_hand", "r_leg", "r_foot", "l_leg", "l_foot", "l_arm", "l_hand")) + if(organ_data[name] == "amputated") continue + if(organ_data[name] == "cyborg") + var/datum/robolimb/R + if(rlimb_data[name]) R = GLOB.all_robolimbs[rlimb_data[name]] + if(!R) R = GLOB.basic_robolimb + if(name == "chest") + name = "torso" + preview_icon.Blend(icon(R.icon, "[name]"), ICON_OVERLAY) // This doesn't check gendered_icon. Not an issue while only limbs can be robotic. + continue + preview_icon.Blend(new /icon(icobase, "[name]"), ICON_OVERLAY) + + // Skin color + if(selected_specie && (selected_specie.bodyflags & HAS_SKIN_COLOR)) + preview_icon.Blend(s_colour, ICON_ADD) + + // Skin tone + if(selected_specie && (selected_specie.bodyflags & HAS_SKIN_TONE)) + if(s_tone >= 0) + preview_icon.Blend(rgb(s_tone, s_tone, s_tone), ICON_ADD) + else + preview_icon.Blend(rgb(-s_tone, -s_tone, -s_tone), ICON_SUBTRACT) + + var/icon/face_s = new/icon("icon" = selected_specie.eyes_icon, "icon_state" = selected_specie.eyes) + if(!(selected_specie.bodyflags & NO_EYES)) + var/icon/eyes_s = new/icon("icon" = selected_specie.eyes_icon, "icon_state" = selected_specie ? selected_specie.eyes : "eyes_s") + eyes_s.Blend(e_colour, ICON_ADD) + face_s.Blend(eyes_s, ICON_OVERLAY) + + preview_icon.Blend(face_s, ICON_OVERLAY) + preview_icon_front = new(preview_icon, dir = SOUTH) + preview_icon_side = new(preview_icon, dir = WEST) //Прок на получение иконки глаз кастомных рас (перезапись, возможно стоит расширить?) /mob/living/carbon/human/get_eyecon()