diff --git a/code/modules/eventkit/event_machinery.dm b/code/modules/eventkit/event_machinery.dm new file mode 100644 index 0000000000..be65102625 --- /dev/null +++ b/code/modules/eventkit/event_machinery.dm @@ -0,0 +1,3 @@ +/obj/machinery/eventkit/custom + name = "Custom Machine" + desc = "A custom machine created by a GM." diff --git a/code/modules/eventkit/gm_interfaces/mob_spawner.dm b/code/modules/eventkit/gm_interfaces/mob_spawner.dm new file mode 100644 index 0000000000..181d5abba6 --- /dev/null +++ b/code/modules/eventkit/gm_interfaces/mob_spawner.dm @@ -0,0 +1,132 @@ +/datum/eventkit/mob_spawner + // The path of the mob to be spawned + var/path + + // Defines if the location of the spawned mob should be bound of the users position + var/loc_lock = FALSE + +/datum/eventkit/mob_spawner/New() + . = ..() + +/datum/eventkit/mob_spawner/tgui_interact(mob/user, datum/tgui/ui) + ui = SStgui.try_update_ui(user, src, ui) + if(!ui) + ui = new(user, src, "MobSpawner", "EventKit - Mob Spawner") + ui.set_autoupdate(FALSE) + ui.open() + +/datum/eventkit/mob_spawner/Destroy() + . = ..() + +/datum/eventkit/mob_spawner/tgui_state(mob/user) + return GLOB.tgui_admin_state + +/datum/eventkit/mob_spawner/tgui_static_data(mob/user) + var/list/data = list() + + data["mob_paths"] = typesof(/mob); + + data["initial_x"] = usr.x; + data["initial_y"] = usr.y; + data["initial_z"] = usr.z; + + return data + +/datum/eventkit/mob_spawner/tgui_data(mob/user) + var/list/data = list() + + data["loc_lock"] = loc_lock; + if(loc_lock) + data["loc_x"] = usr.x; + data["loc_y"] = usr.y; + data["loc_z"] = usr.z; + + data["path"] = path; + + var/mob/M = new path(); + if(M) + data["default_path_name"] = M.name; + data["default_desc"] = M.desc; + data["default_flavor_text"] = M.flavor_text; + qdel(M); + + return data + +/datum/eventkit/mob_spawner/tgui_act(action, list/params) + . = ..() + if(.) + return + if(!check_rights_for(usr.client, R_SPAWN)) + return + switch(action) + if("select_path") + path = params["path"] + return TRUE + if("loc_lock") + loc_lock = !loc_lock + return TRUE + if("start_spawn") + var/confirm = tgui_alert(usr, "Are you sure that you want to start spawning your custom mobs?", "Confirmation", list("Yes", "Cancel")) + + if(confirm != "Yes") + return FALSE + + var/amount = params["amount"] + var/name = params["name"] + var/x = params["x"] + var/y = params["y"] + var/z = params["z"] + + var/turf/T = locate(x, y, z) + if(!T) + to_chat(usr, "Those coordinates are outside the boundaries of the map.") + return FALSE + + for(var/i = 0, i < amount, i++) + if(ispath(path,/turf)) + var/turf/TU = get_turf(locate(x, y, z)) + TU.ChangeTurf(path) + else + var/mob/M = new path(usr.loc) + + M.name = sanitize(name) + M.desc = sanitize(params["desc"]) + M.flavor_text = sanitize(params["flavor_text"]) + + /* + WIP: Radius around selected coords + + var/list/turf/destTurfs + for(var/turf/RT in orange(T, params["r"])) + destTurfs += RT + + var/turf/targetTurf = rand(0,length(destTurfs)) + */ + + var/size_mul = params["size_multiplier"] + if(isnum(size_mul)) + M.size_multiplier = size_mul + M.update_icon() + else + to_chat(usr, "Size Multiplier not applied: ([size_mul]) is not a valid input.") + + M.forceMove(T) + + log_and_message_admins("spawned [path] ([name]) at ([x],[y],[z]) [amount] times.") + + return TRUE + +/datum/eventkit/mob_spawner/tgui_close(mob/user) + . = ..() + qdel(src) + +/client/verb/eventkit_open_mob_spawner() + set category = "EventKit" + set name = "Open Mob Spawner" + set desc = "Opens an advanced version of the mob spawner." + + if(!check_rights(R_SPAWN)) + return + + var/datum/eventkit/mob_spawner/spawner = new() + spawner.tgui_interact(usr) diff --git a/code/modules/vore/resizing/resize_vr.dm b/code/modules/vore/resizing/resize_vr.dm index 4230a82e0b..c168a33416 100644 --- a/code/modules/vore/resizing/resize_vr.dm +++ b/code/modules/vore/resizing/resize_vr.dm @@ -74,9 +74,14 @@ /** * Resizes the mob immediately to the desired mod, animating it growing/shrinking. * It can be used by anything that calls it. + * + * Arguments: + * * new_size - CHANGE_ME. + * * animate - CHANGE_ME. Default: TRUE + * * uncapped - CHANGE_ME. Default: FALSE + * * ignore_prefs - CHANGE_ME. Default: FALSE + * * aura_animation - CHANGE_ME. Default: TRUE */ - - /mob/living/proc/resize(var/new_size, var/animate = TRUE, var/uncapped = FALSE, var/ignore_prefs = FALSE, var/aura_animation = TRUE) if(!uncapped) new_size = clamp(new_size, RESIZE_MINIMUM, RESIZE_MAXIMUM) diff --git a/tgui/packages/tgui/interfaces/MobSpawner.tsx b/tgui/packages/tgui/interfaces/MobSpawner.tsx new file mode 100644 index 0000000000..1f98c55570 --- /dev/null +++ b/tgui/packages/tgui/interfaces/MobSpawner.tsx @@ -0,0 +1,211 @@ +import { BooleanLike } from '../../common/react'; +import { useBackend, useLocalState } from '../backend'; +import { Button, Dropdown, Flex, Input, Knob, LabeledList, NumberInput, Section, Tabs, TextArea } from '../components'; +import { Window } from '../layouts'; + +type Data = { + path: string; + + default_path_name: string; + default_desc: string; + default_flavor_text: string; + + default_speak_emotes: string[]; + + mob_paths: string[]; + + loc_lock: BooleanLike; + loc_x: number; + loc_y: number; + loc_z: number; + + initial_x: number; + initial_y: number; + initial_z: number; +}; + +export const MobSpawner = (props, context) => { + const { act, data } = useBackend(context); + + const [tabIndex, setTabIndex] = useLocalState(context, 'panelTabIndex', 0); + + const tabs: any = []; + + tabs[0] = ; + tabs[1] = ; + + return ( + + + + setTabIndex(0)}> + General Settings + + setTabIndex(1)}> + Vore Settings [WIP] + + + {tabs[tabIndex] || 'Error'} + + + ); +}; + +const GeneralMobSettings = (props, context) => { + const { act, data } = useBackend(context); + + const [amount, setAmount] = useLocalState(context, 'amount', 1); + const [name, setName] = useLocalState( + context, + 'name', + data.default_path_name + ); + const [desc, setDesc] = useLocalState(context, 'desc', data.default_desc); + const [flavorText, setFlavorText] = useLocalState( + context, + 'flavorText', + data.default_flavor_text + ); + + const [sizeMultiplier, setSizeMultiplier] = useLocalState( + context, + 'sizeMultiplier', + 100 + ); + + const [x, setX] = useLocalState(context, 'x', data.initial_x); + const [y, setY] = useLocalState(context, 'y', data.initial_y); + const [z, setZ] = useLocalState(context, 'z', data.initial_z); + + const [radius, setRadius] = useLocalState(context, 'radius', 0); + + return ( + <> +
+ + + setName(val)} + /> + + + act('select_path', { path: val })} + /> + + + setAmount(val)} + /> + + + setSizeMultiplier(val)} + /> + + +
+
+ + + setX(val)} + /> + setY(val)} + /> + setZ(val)} + /> + act('loc_lock')} + /> + + + setRadius(val)} + /> + + +
+
+ + + Description: +
+