mirror of
https://github.com/Bubberstation/Bubberstation.git
synced 2026-08-30 16:47:13 +01:00
TGUI input box conversions 2 (#63395)
More text inputs converted to tgui, TGUI text and number input now more sanely handles ENTER key being pressed, you can now press anywhere in the window to enter the input. TGUI text input now considers placeholder text for the default valid state. IE, if there is default text you can press enter immediately without having to rewrite it just to recheck validity. Fixes: useSharedState => useLocalState. not only was sharedstate not needed but it opened up the ui to vulnerabilities
This commit is contained in:
@@ -74,11 +74,8 @@ GLOBAL_LIST_INIT(typecache_powerfailure_safe_areas, typecacheof(/area/engineerin
|
||||
var/area/newA
|
||||
var/area/oldA = get_area(get_turf(creator))
|
||||
if(!isarea(area_choice))
|
||||
var/str = stripped_input(creator,"New area name:", "Blueprint Editing", "", MAX_NAME_LEN)
|
||||
if(!str || !length(str)) //cancel
|
||||
return
|
||||
if(length(str) > 50)
|
||||
to_chat(creator, span_warning("The given name is too long. The area remains undefined."))
|
||||
var/str = tgui_input_text(creator, "New area name", "Blueprint Editing", max_length = MAX_NAME_LEN)
|
||||
if(!str)
|
||||
return
|
||||
newA = new area_choice
|
||||
newA.setup(str)
|
||||
|
||||
@@ -268,7 +268,7 @@
|
||||
return FALSE
|
||||
|
||||
if(initial(rune_to_scribe.req_keyword))
|
||||
chosen_keyword = stripped_input(cultist, "Enter a keyword for the new rune.", "Words of Power")
|
||||
chosen_keyword = tgui_input_text(cultist, "Keyword for the new rune", "Words of Power", max_length = MAX_NAME_LEN)
|
||||
if(!chosen_keyword)
|
||||
drawing_a_rune = FALSE
|
||||
start_scribe_rune(tool, cultist)
|
||||
|
||||
@@ -149,7 +149,7 @@ GLOBAL_LIST_EMPTY(GPS_list)
|
||||
switch(action)
|
||||
if("rename")
|
||||
var/atom/parentasatom = parent
|
||||
var/a = stripped_input(usr, "Please enter desired tag.", parentasatom.name, gpstag, 20)
|
||||
var/a = tgui_input_text(usr, "Enter the desired tag", "GPS Tag", gpstag, 20)
|
||||
|
||||
if (!a)
|
||||
return
|
||||
|
||||
@@ -74,7 +74,7 @@
|
||||
bound_spirit.copy_languages(awakener, LANGUAGE_MASTER) //Make sure the sword can understand and communicate with the awakener.
|
||||
bound_spirit.update_atom_languages()
|
||||
bound_spirit.grant_all_languages(FALSE, FALSE, TRUE) //Grants omnitongue
|
||||
var/input = sanitize_name(stripped_input(bound_spirit, "What are you named?", ,"", MAX_NAME_LEN))
|
||||
var/input = sanitize_name(tgui_input_text(bound_spirit, "What are you named?", "Spectral Nomenclature", max_length = MAX_NAME_LEN))
|
||||
if(parent && input)
|
||||
parent = input
|
||||
bound_spirit.fully_replace_character_name(null, "The spirit of [input]")
|
||||
|
||||
@@ -219,7 +219,7 @@
|
||||
return FALSE
|
||||
|
||||
tool.play_tool_sound(src)
|
||||
var/input = stripped_input(user, "Which networks would you like to connect this camera to? Separate networks with a comma. No Spaces!\nFor example: SS13,Security,Secret ", "Set Network", "SS13")
|
||||
var/input = tgui_input_text(user, "Which networks would you like to connect this camera to? Separate networks with a comma. No Spaces!\nFor example: SS13,Security,Secret", "Set Network", "SS13", multiline = TRUE)
|
||||
if(!input)
|
||||
to_chat(user, span_warning("No input found, please hang up and try your call again!"))
|
||||
return
|
||||
|
||||
@@ -123,7 +123,7 @@
|
||||
to_chat(usr, span_danger("Unauthorized access."))
|
||||
|
||||
else if(href_list["warn"])
|
||||
var/warning = stripped_input(usr, "Message:", "Enter your message here!", "", MAX_MESSAGE_LEN)
|
||||
var/warning = tgui_input_text(usr, "Enter your message here", "Messaging")
|
||||
if(!warning)
|
||||
return
|
||||
var/obj/item/implant/I = locate(href_list["warn"]) in GLOB.tracked_implants
|
||||
|
||||
@@ -246,7 +246,7 @@ MAPPING_DIRECTIONAL_HELPERS(/obj/machinery/requests_console, 30)
|
||||
if(href_list["write"])
|
||||
to_department = ckey(reject_bad_text(href_list["write"])) //write contains the string of the receiving department's name
|
||||
|
||||
var/new_message = (to_department in GLOB.req_console_ckey_departments) && stripped_input(usr, "Write your message:", "Awaiting Input", "", MAX_MESSAGE_LEN)
|
||||
var/new_message = (to_department in GLOB.req_console_ckey_departments) && tgui_input_text(usr, "Write your message", "Awaiting Input")
|
||||
if(new_message)
|
||||
to_department = GLOB.req_console_ckey_departments[to_department]
|
||||
message = new_message
|
||||
@@ -254,7 +254,7 @@ MAPPING_DIRECTIONAL_HELPERS(/obj/machinery/requests_console, 30)
|
||||
priority = clamp(text2num(href_list["priority"]), REQ_NORMAL_MESSAGE_PRIORITY, REQ_EXTREME_MESSAGE_PRIORITY)
|
||||
|
||||
if(href_list["writeAnnouncement"])
|
||||
var/new_message = reject_bad_text(stripped_input(usr, "Write your message:", "Awaiting Input", "", MAX_MESSAGE_LEN))
|
||||
var/new_message = reject_bad_text(tgui_input_text(usr, "Write your message", "Awaiting Input"))
|
||||
if(new_message)
|
||||
message = new_message
|
||||
priority = clamp(text2num(href_list["priority"]) || REQ_NORMAL_MESSAGE_PRIORITY, REQ_NORMAL_MESSAGE_PRIORITY, REQ_EXTREME_MESSAGE_PRIORITY)
|
||||
|
||||
@@ -171,7 +171,7 @@
|
||||
else
|
||||
var/obj/item/card/id/new_card = W
|
||||
if(new_card.registered_account)
|
||||
var/msg = stripped_input(user, "Name of your roulette wheel:", "Roulette Naming", "Roulette Machine")
|
||||
var/msg = tgui_input_text(user, "Name of your roulette wheel", "Roulette Naming", "Roulette Machine", MAX_NAME_LEN)
|
||||
if(!msg)
|
||||
return
|
||||
name = msg
|
||||
|
||||
@@ -169,7 +169,7 @@ AI MODULES
|
||||
lawpos = 4
|
||||
|
||||
/obj/item/ai_module/supplied/safeguard/attack_self(mob/user)
|
||||
var/targName = stripped_input(user, "Please enter the subject to safeguard.", "Safeguard who?", user.name,MAX_NAME_LEN)
|
||||
var/targName = tgui_input_text(user, "Subject to safeguard.", "Safeguard", user.name, MAX_NAME_LEN)
|
||||
if(!targName)
|
||||
return
|
||||
targetName = targName
|
||||
@@ -195,7 +195,7 @@ AI MODULES
|
||||
laws = list("Only SUBJECT is human.")
|
||||
|
||||
/obj/item/ai_module/zeroth/onehuman/attack_self(mob/user)
|
||||
var/targName = stripped_input(user, "Please enter the subject who is the only human.", "Who?", user.real_name,MAX_NAME_LEN)
|
||||
var/targName = tgui_input_text(user, "Enter the subject who is the only human.", "One Human", user.real_name, MAX_NAME_LEN)
|
||||
if(!targName)
|
||||
return
|
||||
targetName = targName
|
||||
@@ -255,7 +255,7 @@ AI MODULES
|
||||
return
|
||||
newpos = 15
|
||||
lawpos = min(newpos, 50)
|
||||
var/targName = stripped_input(user, "Please enter a new law for the AI.", "Freeform Law Entry", laws[1], CONFIG_GET(number/max_law_len))
|
||||
var/targName = tgui_input_text(user, "Enter a new law for the AI.", "Freeform Law Entry", laws[1], CONFIG_GET(number/max_law_len), TRUE)
|
||||
if(!targName)
|
||||
return
|
||||
if(is_ic_filtered(targName))
|
||||
@@ -386,7 +386,7 @@ AI MODULES
|
||||
var/subject = "human being"
|
||||
|
||||
/obj/item/ai_module/core/full/asimov/attack_self(mob/user as mob)
|
||||
var/targName = stripped_input(user, "Please enter a new subject that asimov is concerned with.", "Asimov to whom?", subject, MAX_NAME_LEN)
|
||||
var/targName = tgui_input_text(user, "Enter a new subject that Asimov is concerned with.", "Asimov", subject, MAX_NAME_LEN)
|
||||
if(!targName)
|
||||
return
|
||||
subject = targName
|
||||
@@ -468,7 +468,7 @@ AI MODULES
|
||||
laws = list("")
|
||||
|
||||
/obj/item/ai_module/core/freeformcore/attack_self(mob/user)
|
||||
var/targName = stripped_input(user, "Please enter a new core law for the AI.", "Freeform Law Entry", laws[1], CONFIG_GET(number/max_law_len))
|
||||
var/targName = tgui_input_text(user, "Enter a new core law for the AI.", "Freeform Law Entry", laws[1], CONFIG_GET(number/max_law_len), TRUE)
|
||||
if(!targName)
|
||||
return
|
||||
if(is_ic_filtered(targName))
|
||||
@@ -496,7 +496,7 @@ AI MODULES
|
||||
laws = list("")
|
||||
|
||||
/obj/item/ai_module/syndicate/attack_self(mob/user)
|
||||
var/targName = stripped_input(user, "Please enter a new law for the AI.", "Freeform Law Entry", laws[1], CONFIG_GET(number/max_law_len))
|
||||
var/targName = tgui_input_text(user, "Enter a new law for the AI", "Freeform Law Entry", laws[1], CONFIG_GET(number/max_law_len), TRUE)
|
||||
if(!targName)
|
||||
return
|
||||
if(is_ic_filtered(targName)) // not even the syndicate can uwu
|
||||
|
||||
@@ -190,7 +190,7 @@
|
||||
/obj/item/areaeditor/proc/edit_area()
|
||||
var/area/A = get_area(usr)
|
||||
var/prevname = "[A.name]"
|
||||
var/str = stripped_input(usr,"New area name:", "Area Creation", "", MAX_NAME_LEN)
|
||||
var/str = tgui_input_text(usr, "New area name", "Area Creation", max_length = MAX_NAME_LEN)
|
||||
if(!str || !length(str) || str==prevname) //cancel
|
||||
return
|
||||
if(length(str) > 50)
|
||||
|
||||
@@ -649,7 +649,7 @@ GLOBAL_LIST_EMPTY(PDAs)
|
||||
if("Clear")//Clears messages
|
||||
tnote = null
|
||||
if("Ringtone")
|
||||
var/t = stripped_input(U, "Please enter new ringtone", name, ttone, 20)
|
||||
var/t = tgui_input_text(U, "Enter a new ringtone", "PDA Ringtone", ttone, 20)
|
||||
if(in_range(src, U) && loc == U && t)
|
||||
if(SEND_SIGNAL(src, COMSIG_PDA_CHANGE_RINGTONE, U, t) & COMPONENT_STOP_RINGTONE_CHANGE)
|
||||
U << browse(null, "window=pda")
|
||||
@@ -767,7 +767,7 @@ GLOBAL_LIST_EMPTY(PDAs)
|
||||
|
||||
|
||||
/obj/item/pda/proc/msg_input(mob/living/U = usr, rigged = FALSE)
|
||||
var/t = stripped_input(U, "Please enter message", name)
|
||||
var/t = tgui_input_text(U, "Enter a message", "PDA Messaging")
|
||||
if (!t || toff)
|
||||
return
|
||||
if(!U.canUseTopic(src, BE_CLOSE))
|
||||
|
||||
@@ -77,10 +77,10 @@
|
||||
return
|
||||
|
||||
var/original_host = host_pda
|
||||
var/fakename = sanitize_name(stripped_input(user, "Enter a name for the rigged message.", "Forge Message", null, MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
var/fakename = sanitize_name(tgui_input_text(user, "Enter a name for the rigged message.", "Forge Message", max_length = MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
if(!fakename || host_pda != original_host || !user.canUseTopic(host_pda, BE_CLOSE))
|
||||
return
|
||||
var/fakejob = sanitize_name(stripped_input(user, "Enter a job for the rigged message.", "Forge Message", null, MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
var/fakejob = sanitize_name(tgui_input_text(user, "Enter a job for the rigged message.", "Forge Message", max_length = MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
if(!fakejob || host_pda != original_host || !user.canUseTopic(host_pda, BE_CLOSE))
|
||||
return
|
||||
if(charges > 0 && host_pda.send_message(user, list(target), rigged = REF(user), fakename = fakename, fakejob = fakejob))
|
||||
|
||||
@@ -33,7 +33,7 @@
|
||||
|
||||
/obj/item/beacon/attackby(obj/item/W, mob/user)
|
||||
if(istype(W, /obj/item/pen)) // needed for things that use custom names like the locator
|
||||
var/new_name = stripped_input(user, "What would you like the name to be?")
|
||||
var/new_name = tgui_input_text(user, "What would you like the name to be?", "Beacon", max_length = MAX_NAME_LEN)
|
||||
if(!user.canUseTopic(src, BE_CLOSE))
|
||||
return
|
||||
if(new_name)
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
if(!user.is_literate())
|
||||
to_chat(user, span_notice("You scribble illegibly on the side of [src]!"))
|
||||
return
|
||||
var/new_name = stripped_input(user, "What would you like the label to be?", name, null)
|
||||
var/new_name = tgui_input_text(user, "What would you like the label to be?", name, max_length = MAX_NAME_LEN)
|
||||
if((user.get_active_held_item() != used_item) || !user.canUseTopic(src, BE_CLOSE))
|
||||
return
|
||||
if(new_name)
|
||||
|
||||
@@ -187,13 +187,13 @@
|
||||
var/objective = "Obey the law. Praise Nanotrasen."
|
||||
var/custom = FALSE
|
||||
|
||||
/obj/machinery/implantchair/brainwash/implant_action(mob/living/C,mob/user)
|
||||
/obj/machinery/implantchair/brainwash/implant_action(mob/living/C, mob/user)
|
||||
if(!istype(C) || !C.mind) // I don't know how this makes any sense for silicons but laws trump objectives anyway.
|
||||
return FALSE
|
||||
if(custom)
|
||||
if(!user || !user.Adjacent(src))
|
||||
return FALSE
|
||||
objective = stripped_input(usr,"What order do you want to imprint on [C]?","Enter the order","",120)
|
||||
objective = tgui_input_text(user, "What order do you want to imprint on [C]?", "Brainwashing", max_length = 120)
|
||||
message_admins("[ADMIN_LOOKUPFLW(user)] set brainwash machine objective to '[objective]'.")
|
||||
log_game("[key_name(user)] set brainwash machine objective to '[objective]'.")
|
||||
if(HAS_TRAIT(C, TRAIT_MINDSHIELD))
|
||||
|
||||
@@ -52,7 +52,7 @@
|
||||
to_chat(user, span_notice("You prod at [src] with [I]!"))
|
||||
return
|
||||
|
||||
var/new_name = stripped_input(user, "What would you like the label to be?", name, null)
|
||||
var/new_name = tgui_input_text(user, "What would you like the label to be?", name, max_length = MAX_NAME_LEN)
|
||||
if(user.get_active_held_item() != I)
|
||||
return
|
||||
if(!user.canUseTopic(src, BE_CLOSE))
|
||||
|
||||
@@ -40,7 +40,7 @@
|
||||
one_use = TRUE
|
||||
|
||||
/obj/item/borg/upgrade/rename/attack_self(mob/user)
|
||||
heldname = sanitize_name(stripped_input(user, "Enter new robot name", "Cyborg Reclassification", heldname, MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
heldname = sanitize_name(tgui_input_text(user, "Enter new robot name", "Cyborg Reclassification", heldname, MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
log_game("[key_name(user)] have set \"[heldname]\" as a name in a cyborg reclassification board at [loc_name(user)]")
|
||||
|
||||
/obj/item/borg/upgrade/rename/action(mob/living/silicon/robot/R, user = usr)
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
if(!user.is_literate())
|
||||
to_chat(user, span_notice("You scribble illegibly on [src]!"))
|
||||
return
|
||||
var/txt = stripped_input(user, "What would you like to write on the sign?", "Sign Label", null , 30)
|
||||
var/txt = tgui_input_text(user, "What would you like to write on the sign?", "Sign Label", max_length = 30)
|
||||
if(txt && user.canUseTopic(src, BE_CLOSE))
|
||||
label = txt
|
||||
name = "[label] sign"
|
||||
|
||||
@@ -122,7 +122,7 @@
|
||||
if(user.canUseTopic(src, BE_CLOSE))
|
||||
..()
|
||||
if(istype(user) && loc == user)
|
||||
var/input = stripped_input(user,"What do you want your war cry to be? You will shout it when you hit someone in melee.", ,"", 50)
|
||||
var/input = tgui_input_text(user, "What do you want your war cry to be? You will shout it when you hit someone in melee.", "War Cry", max_length = 50)
|
||||
if(input)
|
||||
src.war_cry = input
|
||||
|
||||
|
||||
@@ -1467,7 +1467,7 @@
|
||||
|
||||
//Add changing looks when i feel suicidal about making 20 inhands for these.
|
||||
/obj/item/toy/dummy/attack_self(mob/user)
|
||||
var/new_name = stripped_input(usr,"What would you like to name the dummy?","Input a name",doll_name,MAX_NAME_LEN)
|
||||
var/new_name = tgui_input_text(usr, "What would you like to name the dummy?", "Doll Name", doll_name, MAX_NAME_LEN)
|
||||
if(!new_name)
|
||||
return
|
||||
doll_name = new_name
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
return
|
||||
|
||||
to_chat(joe, span_notice("As you burn the picture, a nickname comes to mind..."))
|
||||
var/nickname = stripped_input(joe, "Pick a nickname", "Mafioso Nicknames", null, NICKNAME_CAP, TRUE)
|
||||
var/nickname = tgui_input_text(joe, "Pick a nickname", "Mafioso Nicknames", max_length = NICKNAME_CAP)
|
||||
nickname = reject_bad_name(nickname, allow_numbers = FALSE, max_length = NICKNAME_CAP, ascii_only = TRUE)
|
||||
if(!nickname)
|
||||
return
|
||||
|
||||
@@ -353,7 +353,7 @@
|
||||
|
||||
trophy_message = W.desc //default value
|
||||
|
||||
var/chosen_plaque = stripped_input(user, "What would you like the plaque to say? Default value is item's description.", "Trophy Plaque")
|
||||
var/chosen_plaque = tgui_input_text(user, "What would you like the plaque to say? Default value is item's description.", "Trophy Plaque", trophy_message)
|
||||
if(chosen_plaque)
|
||||
if(user.Adjacent(src))
|
||||
trophy_message = chosen_plaque
|
||||
|
||||
@@ -51,7 +51,7 @@
|
||||
|
||||
/obj/structure/door_assembly/attackby(obj/item/W, mob/user, params)
|
||||
if(istype(W, /obj/item/pen))
|
||||
var/t = stripped_input(user, "Enter the name for the door.", name, created_name,MAX_NAME_LEN)
|
||||
var/t = tgui_input_text(user, "Enter the name for the door.", name, created_name, MAX_NAME_LEN)
|
||||
if(!t)
|
||||
return
|
||||
if(!in_range(src, usr) && loc != usr)
|
||||
|
||||
@@ -139,7 +139,7 @@
|
||||
message_admins("[key_name_admin(user)] disabled scrambled codes on [ADMIN_LOOKUPFLW(borg)].")
|
||||
log_silicon("[key_name(user)] disabled scrambled codes on [key_name(borg)].")
|
||||
if ("rename")
|
||||
var/new_name = sanitize_name(stripped_input(user,"What would you like to name this cyborg?","Input a name",borg.real_name,MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
var/new_name = sanitize_name(tgui_input_text(user, "What would you like to name this cyborg?", "Cyborg Reclassification", borg.real_name, MAX_NAME_LEN), allow_numbers = TRUE)
|
||||
if(!new_name)
|
||||
return
|
||||
message_admins("[key_name_admin(user)] renamed [ADMIN_LOOKUPFLW(borg)] to [new_name].")
|
||||
|
||||
@@ -332,8 +332,8 @@
|
||||
to_chat(user, span_warning("Your target is already under a mind-controlling influence!"))
|
||||
return
|
||||
|
||||
var/command = stripped_input(user, "Enter the command for your target to follow.\
|
||||
Uses Left: [G.mind_control_uses], Duration: [DisplayTimeText(G.mind_control_duration)]","Enter command")
|
||||
var/command = tgui_input_text(user, "Enter the command for your target to follow.\
|
||||
Uses Left: [G.mind_control_uses], Duration: [DisplayTimeText(G.mind_control_duration)]", "Enter command")
|
||||
|
||||
if(!command)
|
||||
return
|
||||
@@ -357,7 +357,7 @@
|
||||
if(L.stat == DEAD)
|
||||
to_chat(user, span_warning("Your target is dead!"))
|
||||
return
|
||||
var/message = stripped_input(user, "Write a message to send to your target's brain.","Enter message")
|
||||
var/message = tgui_input_text(user, "Message to send to your target's brain", "Enter message")
|
||||
if(!message)
|
||||
return
|
||||
if(QDELETED(L) || L.stat == DEAD)
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
to_chat(user, span_notice("We return our vocal glands to their original position."))
|
||||
return
|
||||
|
||||
var/mimic_voice = sanitize_name(stripped_input(user, "Enter a name to mimic.", "Mimic Voice", null, MAX_NAME_LEN))
|
||||
var/mimic_voice = sanitize_name(tgui_input_text(user, "Enter a name to mimic", "Mimic Voice", max_length = MAX_NAME_LEN))
|
||||
if(!mimic_voice)
|
||||
return
|
||||
..()
|
||||
|
||||
@@ -39,7 +39,7 @@
|
||||
if(turf_check(T))
|
||||
var/chosen_keyword
|
||||
if(initial(rune_type.req_keyword))
|
||||
chosen_keyword = stripped_input(owner, "Enter a keyword for the new rune.", "Words of Power")
|
||||
chosen_keyword = tgui_input_text(owner, "Enter a keyword for the new rune.", "Words of Power", max_length = MAX_NAME_LEN)
|
||||
if(!chosen_keyword)
|
||||
return
|
||||
//the outer ring is always the same across all runes
|
||||
|
||||
@@ -172,7 +172,7 @@ the new instance inside the host to be updated to the template's stats.
|
||||
taken_names[initial(D.name)] = TRUE
|
||||
var/set_name
|
||||
while(!set_name)
|
||||
var/input = sanitize_name(stripped_input(src, "Select a name for your disease", "Select Name", "", MAX_NAME_LEN))
|
||||
var/input = sanitize_name(tgui_input_text(src, "Select a name for your disease", "Select Name", max_length = MAX_NAME_LEN))
|
||||
if(!input)
|
||||
set_name = "Sentient Virus"
|
||||
break
|
||||
|
||||
@@ -44,7 +44,7 @@ GLOBAL_LIST_EMPTY(jam_on_wardec)
|
||||
|
||||
if(custom_threat == "Yes")
|
||||
declaring_war = TRUE
|
||||
war_declaration = stripped_input(user, "Insert your custom declaration", "Declaration")
|
||||
war_declaration = tgui_input_text(user, "Insert your custom declaration", "Declaration", multiline = TRUE)
|
||||
declaring_war = FALSE
|
||||
|
||||
if(!check_allowed(user) || !war_declaration)
|
||||
@@ -80,7 +80,7 @@ GLOBAL_LIST_EMPTY(jam_on_wardec)
|
||||
var/custom_threat = tgui_alert(usr, "Do you want to customize the declaration?", "Customize?", list("Yes", "No"))
|
||||
|
||||
if(custom_threat == "Yes")
|
||||
war_declaration = stripped_input(usr, "Insert your custom declaration", "Declaration")
|
||||
war_declaration = tgui_input_text(usr, "Insert your custom declaration", "Declaration", multiline = TRUE)
|
||||
|
||||
if(!war_declaration)
|
||||
to_chat(usr, span_warning("Invalid war declaration."))
|
||||
|
||||
@@ -178,7 +178,7 @@
|
||||
var/wizard_name_second = pick(GLOB.wizard_second)
|
||||
var/randomname = "[wizard_name_first] [wizard_name_second]"
|
||||
var/mob/living/wiz_mob = owner.current
|
||||
var/newname = sanitize_name(reject_bad_text(stripped_input(wiz_mob, "You are the [name]. Would you like to change your name to something else?", "Name change", randomname, MAX_NAME_LEN)))
|
||||
var/newname = sanitize_name(reject_bad_text(tgui_input_text(wiz_mob, "You are the [name]. Would you like to change your name to something else?", "Name change", randomname, MAX_NAME_LEN)))
|
||||
|
||||
if (!newname)
|
||||
newname = randomname
|
||||
|
||||
@@ -6,13 +6,13 @@
|
||||
* validate the input inside the UI and ui_act.
|
||||
*
|
||||
* Arguments:
|
||||
* * user - The user to show the numbox to.
|
||||
* * message - The content of the numbox, shown in the body of the TGUI window.
|
||||
* * title - The title of the numbox modal, shown on the top of the TGUI window.
|
||||
* * user - The user to show the number input to.
|
||||
* * message - The content of the number input, shown in the body of the TGUI window.
|
||||
* * title - The title of the number input modal, shown on the top of the TGUI window.
|
||||
* * default - The default (or current) value, shown as a placeholder. Users can press refresh with this.
|
||||
* * max_value - Specifies a maximum value. If none is set, any number can be entered. Pressing "max" defaults to 1000.
|
||||
* * min_value - Specifies a minimum value. Often 0.
|
||||
* * timeout - The timeout of the numbox, after which the modal will close and qdel itself. Set to zero for no timeout.
|
||||
* * timeout - The timeout of the number input, after which the modal will close and qdel itself. Set to zero for no timeout.
|
||||
*/
|
||||
/proc/tgui_input_number(mob/user, message = null, title = "Number Input", default = null, max_value = null, min_value = 0, timeout = 0)
|
||||
if (!user)
|
||||
@@ -26,29 +26,29 @@
|
||||
/// Client does NOT have tgui_input on: Returns regular input
|
||||
if(!user.client.prefs.read_preference(/datum/preference/toggle/tgui_input))
|
||||
return input(user, message, title, default) as null|num
|
||||
var/datum/tgui_input_number/numbox = new(user, message, title, default, max_value, min_value, timeout)
|
||||
numbox.ui_interact(user)
|
||||
numbox.wait()
|
||||
if (numbox)
|
||||
. = numbox.entry
|
||||
qdel(numbox)
|
||||
var/datum/tgui_input_number/number_input = new(user, message, title, default, max_value, min_value, timeout)
|
||||
number_input.ui_interact(user)
|
||||
number_input.wait()
|
||||
if (number_input)
|
||||
. = number_input.entry
|
||||
qdel(number_input)
|
||||
|
||||
/**
|
||||
* Creates an asynchronous TGUI number input window with an associated callback.
|
||||
*
|
||||
* This proc should be used to create numboxes that invoke a callback with the user's entry.
|
||||
* This proc should be used to create number inputs that invoke a callback with the user's entry.
|
||||
*
|
||||
* Arguments:
|
||||
* * user - The user to show the numbox to.
|
||||
* * message - The content of the numbox, shown in the body of the TGUI window.
|
||||
* * title - The title of the numbox modal, shown on the top of the TGUI window.
|
||||
* * user - The user to show the number input to.
|
||||
* * message - The content of the number input, shown in the body of the TGUI window.
|
||||
* * title - The title of the number input modal, shown on the top of the TGUI window.
|
||||
* * default - The default (or current) value, shown as a placeholder. Users can press refresh with this.
|
||||
* * max_value - Specifies a maximum value. If none is set, any number can be entered. Pressing "max" defaults to 1000.
|
||||
* * min_value - Specifies a minimum value. Often 0.
|
||||
* * callback - The callback to be invoked when a choice is made.
|
||||
* * timeout - The timeout of the numbox, after which the modal will close and qdel itself. Disabled by default, can be set to seconds otherwise.
|
||||
* * timeout - The timeout of the number input, after which the modal will close and qdel itself. Set to zero for no timeout.
|
||||
*/
|
||||
/proc/tgui_input_number_async(mob/user, message = null, title = "Number Input", default = null, max_value = null, min_value = 0, datum/callback/callback, timeout = 0)
|
||||
/proc/tgui_input_number_async(mob/user, message = null, title = "Number Input", default = null, max_value = null, min_value = 0, datum/callback/callback, timeout = 60 SECONDS)
|
||||
if (!user)
|
||||
user = usr
|
||||
if (!istype(user))
|
||||
@@ -57,14 +57,14 @@
|
||||
user = client.mob
|
||||
else
|
||||
return
|
||||
var/datum/tgui_input_number/async/numbox = new(user, message, title, default, max_value, min_value, callback, timeout)
|
||||
numbox.ui_interact(user)
|
||||
var/datum/tgui_input_number/async/number_input = new(user, message, title, default, max_value, min_value, callback, timeout)
|
||||
number_input.ui_interact(user)
|
||||
|
||||
/**
|
||||
* # tgui_input_number
|
||||
*
|
||||
* Datum used for instantiating and using a TGUI-controlled numbox that prompts the user with
|
||||
* a message and has an input for text entry.
|
||||
* Datum used for instantiating and using a TGUI-controlled number input that prompts the user with
|
||||
* a message and has an input for number entry.
|
||||
*/
|
||||
/datum/tgui_input_number
|
||||
/// Boolean field describing if the tgui_input_number was closed by the user.
|
||||
@@ -79,9 +79,9 @@
|
||||
var/message
|
||||
/// The minimum value that can be entered.
|
||||
var/min_value
|
||||
/// The time at which the tgui_modal was created, for displaying timeout progress.
|
||||
/// The time at which the number input was created, for displaying timeout progress.
|
||||
var/start_time
|
||||
/// The lifespan of the tgui_input_number, after which the window will close and delete itself.
|
||||
/// The lifespan of the number input, after which the window will close and delete itself.
|
||||
var/timeout
|
||||
/// The title of the TGUI window
|
||||
var/title
|
||||
@@ -114,6 +114,7 @@
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, "NumberInputModal")
|
||||
ui.set_autoupdate(FALSE)
|
||||
ui.open()
|
||||
|
||||
/datum/tgui_input_number/ui_close(mob/user)
|
||||
@@ -125,19 +126,18 @@
|
||||
|
||||
/datum/tgui_input_number/ui_static_data(mob/user)
|
||||
. = list(
|
||||
"preferences" = list()
|
||||
"max_value" = max_value,
|
||||
"message" = message,
|
||||
"min_value" = min_value,
|
||||
"placeholder" = default, /// You cannot use default as a const
|
||||
"preferences" = list(),
|
||||
"title" = title
|
||||
)
|
||||
.["preferences"]["large_buttons"] = user.client.prefs.read_preference(/datum/preference/toggle/tgui_input_large)
|
||||
.["preferences"]["swapped_buttons"] = user.client.prefs.read_preference(/datum/preference/toggle/tgui_input_swapped)
|
||||
|
||||
/datum/tgui_input_number/ui_data(mob/user)
|
||||
. = list(
|
||||
"max_value" = max_value,
|
||||
"message" = message,
|
||||
"min_value" = min_value,
|
||||
"placeholder" = default, /// You cannot use default as a const
|
||||
"title" = title,
|
||||
)
|
||||
. = list()
|
||||
if(timeout)
|
||||
.["timeout"] = CLAMP01((timeout - (world.time - start_time) - 1 SECONDS) / (timeout - 1 SECONDS))
|
||||
|
||||
|
||||
@@ -6,9 +6,9 @@
|
||||
* stripped_multiline_input.
|
||||
*
|
||||
* Arguments:
|
||||
* * user - The user to show the textbox to.
|
||||
* * message - The content of the textbox, shown in the body of the TGUI window.
|
||||
* * title - The title of the textbox modal, shown on the top of the TGUI window.
|
||||
* * user - The user to show the text input to.
|
||||
* * message - The content of the text input, shown in the body of the TGUI window.
|
||||
* * title - The title of the text input modal, shown on the top of the TGUI window.
|
||||
* * default - The default (or current) value, shown as a placeholder.
|
||||
* * max_length - Specifies a max length for input. MAX_MESSAGE_LEN is default (1024)
|
||||
* * multiline - Bool that determines if the input box is much larger. Good for large messages, laws, etc.
|
||||
@@ -33,29 +33,28 @@
|
||||
return stripped_input(user, message, title, default, max_length)
|
||||
else
|
||||
return input(user, message, title, default)
|
||||
var/datum/tgui_input_text/textbox = new(user, message, title, default, max_length, multiline, encode, timeout)
|
||||
textbox.ui_interact(user)
|
||||
textbox.wait()
|
||||
if (textbox)
|
||||
. = textbox.entry
|
||||
qdel(textbox)
|
||||
var/datum/tgui_input_text/text_input = new(user, message, title, default, max_length, multiline, encode, timeout)
|
||||
text_input.ui_interact(user)
|
||||
text_input.wait()
|
||||
if (text_input)
|
||||
. = text_input.entry
|
||||
qdel(text_input)
|
||||
|
||||
/**
|
||||
* Creates an asynchronous TGUI text input window with an associated callback.
|
||||
*
|
||||
* This proc should be used to create textboxes that invoke a callback with the user's entry.
|
||||
* This proc should be used to create text inputs that invoke a callback with the user's entry.
|
||||
* Arguments:
|
||||
* * user - The user to show the textbox to.
|
||||
* * message - The content of the textbox, shown in the body of the TGUI window.
|
||||
* * title - The title of the textbox modal, shown on the top of the TGUI window.
|
||||
* * user - The user to show the text input to.
|
||||
* * message - The content of the text input, shown in the body of the TGUI window.
|
||||
* * title - The title of the text input modal, shown on the top of the TGUI window.
|
||||
* * default - The default (or current) value, shown as a placeholder.
|
||||
* * max_length - Specifies a max length for input.
|
||||
* * multiline - Bool that determines if the input box is much larger. Good for large messages, laws, etc.
|
||||
* * encode - If toggled, input is filtered via html_encode. Setting this to FALSE gives raw input.
|
||||
* * callback - The callback to be invoked when a choice is made.
|
||||
* * timeout - The timeout of the textbox, after which the modal will close and qdel itself. Disabled by default, can be set to seconds otherwise.
|
||||
*/
|
||||
/proc/tgui_input_text_async(mob/user, message = null, title = "Text Input", default = null, max_length = null, multiline = FALSE, encode = TRUE, datum/callback/callback, timeout = 0)
|
||||
/proc/tgui_input_text_async(mob/user, message = null, title = "Text Input", default = null, max_length = null, multiline = FALSE, encode = TRUE, datum/callback/callback, timeout = 60 SECONDS)
|
||||
if (!user)
|
||||
user = usr
|
||||
if (!istype(user))
|
||||
@@ -64,13 +63,13 @@
|
||||
user = client.mob
|
||||
else
|
||||
return
|
||||
var/datum/tgui_input_text/async/textbox = new(user, message, title, default, max_length, multiline, encode, callback, timeout)
|
||||
textbox.ui_interact(user)
|
||||
var/datum/tgui_input_text/async/text_input = new(user, message, title, default, max_length, multiline, encode, callback, timeout)
|
||||
text_input.ui_interact(user)
|
||||
|
||||
/**
|
||||
* # tgui_input_text
|
||||
*
|
||||
* Datum used for instantiating and using a TGUI-controlled textbox that prompts the user with
|
||||
* Datum used for instantiating and using a TGUI-controlled text input that prompts the user with
|
||||
* a message and has an input for text entry.
|
||||
*/
|
||||
/datum/tgui_input_text
|
||||
@@ -88,9 +87,9 @@
|
||||
var/message
|
||||
/// Multiline input for larger input boxes.
|
||||
var/multiline
|
||||
/// The time at which the tgui_modal was created, for displaying timeout progress.
|
||||
/// The time at which the text input was created, for displaying timeout progress.
|
||||
var/start_time
|
||||
/// The lifespan of the tgui_input_text, after which the window will close and delete itself.
|
||||
/// The lifespan of the text input, after which the window will close and delete itself.
|
||||
var/timeout
|
||||
/// The title of the TGUI window
|
||||
var/title
|
||||
@@ -124,6 +123,7 @@
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, "TextInputModal")
|
||||
ui.set_autoupdate(FALSE)
|
||||
ui.open()
|
||||
|
||||
/datum/tgui_input_text/ui_close(mob/user)
|
||||
@@ -135,19 +135,18 @@
|
||||
|
||||
/datum/tgui_input_text/ui_static_data(mob/user)
|
||||
. = list(
|
||||
"preferences" = list()
|
||||
"max_length" = max_length,
|
||||
"message" = message,
|
||||
"multiline" = multiline,
|
||||
"placeholder" = default, /// You cannot use default as a const
|
||||
"preferences" = list(),
|
||||
"title" = title
|
||||
)
|
||||
.["preferences"]["large_buttons"] = user.client.prefs.read_preference(/datum/preference/toggle/tgui_input_large)
|
||||
.["preferences"]["swapped_buttons"] = user.client.prefs.read_preference(/datum/preference/toggle/tgui_input_swapped)
|
||||
|
||||
/datum/tgui_input_text/ui_data(mob/user)
|
||||
. = list(
|
||||
"max_length" = max_length,
|
||||
"message" = message,
|
||||
"multiline" = multiline,
|
||||
"placeholder" = default, /// You cannot use default as a const
|
||||
"title" = title,
|
||||
)
|
||||
. = list()
|
||||
if(timeout)
|
||||
.["timeout"] = CLAMP01((timeout - (world.time - start_time) - 1 SECONDS) / (timeout - 1 SECONDS))
|
||||
|
||||
|
||||
@@ -1214,9 +1214,9 @@ GLOBAL_LIST_EMPTY(vending_products)
|
||||
|
||||
if(compartmentLoadAccessCheck(user))
|
||||
if(istype(I, /obj/item/pen))
|
||||
name = stripped_input(user,"Set name","Name", name, 20)
|
||||
desc = stripped_input(user,"Set description","Description", desc, 60)
|
||||
slogan_list += stripped_input(user,"Set slogan","Slogan","Epic", 60)
|
||||
name = tgui_input_text(user, "Set name", "Name", name, 20)
|
||||
desc = tgui_input_text(user, "Set description", "Description", desc, 60)
|
||||
slogan_list += tgui_input_text(user, "Set slogan", "Slogan", "Epic", 60)
|
||||
last_slogan = world.time + rand(0, slogan_delay)
|
||||
return
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { Loader } from './common/Loader';
|
||||
import { InputButtons, Preferences } from './common/InputButtons';
|
||||
import { KEY_ENTER } from 'common/keycodes';
|
||||
import { useBackend, useSharedState } from '../backend';
|
||||
import { useBackend, useLocalState } from '../backend';
|
||||
import { Box, Button, NumberInput, Section, Stack } from '../components';
|
||||
import { Window } from '../layouts';
|
||||
|
||||
@@ -16,10 +16,10 @@ type NumberInputData = {
|
||||
};
|
||||
|
||||
export const NumberInputModal = (_, context) => {
|
||||
const { data } = useBackend<NumberInputData>(context);
|
||||
const { act, data } = useBackend<NumberInputData>(context);
|
||||
const { message, placeholder, preferences, timeout, title } = data;
|
||||
const { large_buttons } = preferences;
|
||||
const [input, setInput] = useSharedState(context, 'input', placeholder);
|
||||
const [input, setInput] = useLocalState(context, 'input', placeholder);
|
||||
const onChange = (value: number) => {
|
||||
setInput(value);
|
||||
};
|
||||
@@ -35,7 +35,13 @@ export const NumberInputModal = (_, context) => {
|
||||
return (
|
||||
<Window title={title} width={270} height={windowHeight}>
|
||||
{timeout && <Loader value={timeout} />}
|
||||
<Window.Content>
|
||||
<Window.Content
|
||||
onKeyDown={(event) => {
|
||||
const keyCode = window.event ? event.which : event.keyCode;
|
||||
if (keyCode === KEY_ENTER) {
|
||||
act('submit', { entry: input });
|
||||
}
|
||||
}}>
|
||||
<Section fill>
|
||||
<Stack fill vertical>
|
||||
<Stack.Item>
|
||||
@@ -77,12 +83,6 @@ const InputArea = (props, context) => {
|
||||
maxValue={max_value}
|
||||
onChange={(_, value) => onChange(value)}
|
||||
onDrag={(_, value) => onChange(value)}
|
||||
onKeyDown={(event) => {
|
||||
const keyCode = window.event ? event.which : event.keyCode;
|
||||
if (keyCode === KEY_ENTER && input) {
|
||||
act('submit', { entry: input });
|
||||
}
|
||||
}}
|
||||
value={input || placeholder || 0}
|
||||
/>
|
||||
</Stack.Item>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { useBackend, useSharedState } from '../backend';
|
||||
import { useBackend, useLocalState } from '../backend';
|
||||
import { Box, Button, LabeledList, Icon, NoticeBox, ProgressBar, Section, Stack, Table, Tabs, Tooltip } from '../components';
|
||||
import { Window } from '../layouts';
|
||||
|
||||
@@ -104,7 +104,7 @@ const ICON_MAP = {
|
||||
};
|
||||
|
||||
export const PaiInterface = (_, context) => {
|
||||
const [tab, setTab] = useSharedState(context, 'tab', 1);
|
||||
const [tab, setTab] = useLocalState(context, 'tab', 1);
|
||||
const setTabHandler = (tab: number) => {
|
||||
setTab(tab);
|
||||
};
|
||||
@@ -299,7 +299,7 @@ const DirectiveDisplay = (_, context) => {
|
||||
* software info.
|
||||
*/
|
||||
const InstalledDisplay = (_, context) => {
|
||||
const [installSelected, setInstallSelected] = useSharedState(
|
||||
const [installSelected, setInstallSelected] = useLocalState(
|
||||
context,
|
||||
'software',
|
||||
''
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { Loader } from './common/Loader';
|
||||
import { InputButtons, Preferences, Validator } from './common/InputButtons';
|
||||
import { useBackend, useSharedState } from '../backend';
|
||||
import { useBackend, useLocalState } from '../backend';
|
||||
import { KEY_ENTER } from 'common/keycodes';
|
||||
import { Box, Input, Section, Stack, TextArea } from '../components';
|
||||
import { Window } from '../layouts';
|
||||
@@ -16,7 +16,7 @@ type TextInputData = {
|
||||
};
|
||||
|
||||
export const TextInputModal = (_, context) => {
|
||||
const { data } = useBackend<TextInputData>(context);
|
||||
const { act, data } = useBackend<TextInputData>(context);
|
||||
const {
|
||||
max_length,
|
||||
message,
|
||||
@@ -27,26 +27,37 @@ export const TextInputModal = (_, context) => {
|
||||
title,
|
||||
} = data;
|
||||
const { large_buttons } = preferences;
|
||||
const [input, setInput] = useSharedState(context, 'input', placeholder);
|
||||
const [inputIsValid, setInputIsValid] = useSharedState<Validator>(
|
||||
const [input, setInput] = useLocalState<string>(
|
||||
context,
|
||||
'input',
|
||||
placeholder || ''
|
||||
);
|
||||
const [inputIsValid, setInputIsValid] = useLocalState<Validator>(
|
||||
context,
|
||||
'inputIsValid',
|
||||
{ isValid: false, error: null }
|
||||
{ isValid: !!placeholder, error: null }
|
||||
);
|
||||
const onType = (event) => {
|
||||
event.preventDefault();
|
||||
const target = event.target;
|
||||
setInputIsValid(validateInput(target.value, max_length));
|
||||
setInput(target.value);
|
||||
const onType = (value: string) => {
|
||||
setInputIsValid(validateInput(value, max_length));
|
||||
setInput(value);
|
||||
};
|
||||
// Dynamically changes the window height based on the message.
|
||||
const windowHeight
|
||||
= 125 + Math.ceil(message?.length / 3) + (multiline ? 75 : 0);
|
||||
= 125
|
||||
+ Math.ceil(message?.length / 3)
|
||||
+ (multiline ? 75 : 0)
|
||||
+ (large_buttons ? 5 : 0);
|
||||
|
||||
return (
|
||||
<Window title={title} width={325} height={windowHeight}>
|
||||
{timeout && <Loader value={timeout} />}
|
||||
<Window.Content>
|
||||
<Window.Content
|
||||
onKeyDown={(event) => {
|
||||
const keyCode = window.event ? event.which : event.keyCode;
|
||||
if (keyCode === KEY_ENTER && inputIsValid.isValid) {
|
||||
act('submit', { entry: input });
|
||||
}
|
||||
}}>
|
||||
<Section fill>
|
||||
<Stack fill vertical>
|
||||
<Stack.Item>
|
||||
@@ -69,9 +80,9 @@ export const TextInputModal = (_, context) => {
|
||||
|
||||
/** Gets the user input and invalidates if there's a constraint. */
|
||||
const InputArea = (props, context) => {
|
||||
const { act, data } = useBackend<TextInputData>(context);
|
||||
const { data } = useBackend<TextInputData>(context);
|
||||
const { multiline } = data;
|
||||
const { input, inputIsValid, onType } = props;
|
||||
const { input, onType } = props;
|
||||
|
||||
if (!multiline) {
|
||||
return (
|
||||
@@ -79,13 +90,7 @@ const InputArea = (props, context) => {
|
||||
<Input
|
||||
autoFocus
|
||||
fluid
|
||||
onInput={(event) => onType(event)}
|
||||
onKeyDown={(event) => {
|
||||
const keyCode = window.event ? event.which : event.keyCode;
|
||||
if (keyCode === KEY_ENTER && inputIsValid) {
|
||||
act('submit', { entry: input });
|
||||
}
|
||||
}}
|
||||
onInput={(_, value) => onType(value)}
|
||||
placeholder="Type something..."
|
||||
value={input}
|
||||
/>
|
||||
@@ -97,14 +102,7 @@ const InputArea = (props, context) => {
|
||||
<TextArea
|
||||
autoFocus
|
||||
height="100%"
|
||||
onInput={(event) => onType(event)}
|
||||
onKeyDown={(event) => {
|
||||
const keyCode = window.event ? event.which : event.keyCode;
|
||||
if (keyCode === KEY_ENTER && inputIsValid) {
|
||||
|
||||
act('submit', { entry: input });
|
||||
}
|
||||
}}
|
||||
onInput={(_, value) => onType(value)}
|
||||
placeholder="Type something..."
|
||||
value={input}
|
||||
/>
|
||||
|
||||
Reference in New Issue
Block a user