diff --git a/code/_globalvars/lists/names.dm b/code/_globalvars/lists/names.dm
index 0a9818d49a6..63ab782dd42 100644
--- a/code/_globalvars/lists/names.dm
+++ b/code/_globalvars/lists/names.dm
@@ -28,3 +28,23 @@ GLOBAL_LIST_INIT(adjectives, world.file2list("strings/names/adjectives.txt"))
GLOBAL_LIST_INIT(dream_strings, world.file2list("strings/dreamstrings.txt"))
//loaded on startup because of "
//would include in rsc if ' was used
+
+/*
+List of configurable names in preferences and their metadata
+"id" = list(
+ "pref_name" = "name", //pref label
+ "qdesc" = "name", //popup question text
+ "allow_numbers" = FALSE, // numbers allowed in the name
+ "group" = "whatever", // group (these will be grouped together on pref ui ,order still follows the list so they need to be concurrent to be grouped)
+ "allow_null" = FALSE // if empty name is entered it's replaced with default value
+ ),
+*/
+GLOBAL_LIST_INIT(preferences_custom_names, list(
+ "human" = list("pref_name" = "Backup Human", "qdesc" = "backup human name, used in the event you are assigned a command role as another species", "allow_numbers" = FALSE , "group" = "backup_human", "allow_null" = FALSE),
+ "clown" = list("pref_name" = "Clown" , "qdesc" = "clown name", "allow_numbers" = FALSE , "group" = "fun", "allow_null" = FALSE),
+ "mime" = list("pref_name" = "Mime", "qdesc" = "mime name" , "allow_numbers" = FALSE , "group" = "fun", "allow_null" = FALSE),
+ "cyborg" = list("pref_name" = "Cyborg", "qdesc" = "cyborg name (Leave empty to use default naming scheme)", "allow_numbers" = TRUE , "group" = "silicons", "allow_null" = TRUE),
+ "ai" = list("pref_name" = "AI", "qdesc" = "ai name", "allow_numbers" = TRUE , "group" = "silicons", "allow_null" = FALSE),
+ "religion" = list("pref_name" = "Chaplain religion", "qdesc" = "religion" , "allow_numbers" = TRUE , "group" = "chaplain", "allow_null" = FALSE),
+ "deity" = list("pref_name" = "Chaplain deity", "qdesc" = "deity", "allow_numbers" = TRUE , "group" = "chaplain", "allow_null" = FALSE)
+ ))
diff --git a/code/modules/client/preferences.dm b/code/modules/client/preferences.dm
index a05826d02d4..678e7eccfa9 100644
--- a/code/modules/client/preferences.dm
+++ b/code/modules/client/preferences.dm
@@ -70,7 +70,7 @@ GLOBAL_LIST_EMPTY(preferences_datums)
var/datum/species/pref_species = new /datum/species/human() //Mutant race
var/list/features = list("mcolor" = "FFF", "tail_lizard" = "Smooth", "tail_human" = "None", "snout" = "Round", "horns" = "None", "ears" = "None", "wings" = "None", "frills" = "None", "spines" = "None", "body_markings" = "None", "legs" = "Normal Legs", "moth_wings" = "Plain")
- var/list/custom_names = list("human", "clown", "mime", "ai", "cyborg", "religion", "deity")
+ var/list/custom_names = list()
var/prefered_security_department = SEC_DEPT_RANDOM
//Mob preview
@@ -122,11 +122,10 @@ GLOBAL_LIST_EMPTY(preferences_datums)
/datum/preferences/New(client/C)
parent = C
- custom_names["human"] = random_unique_name()
- custom_names["ai"] = pick(GLOB.ai_names)
- custom_names["cyborg"] = DEFAULT_CYBORG_NAME
- custom_names["clown"] = pick(GLOB.clown_names)
- custom_names["mime"] = pick(GLOB.mime_names)
+
+ for(var/custom_name_id in GLOB.preferences_custom_names)
+ custom_names[custom_name_id] = get_default_name(custom_name_id)
+
UI_style = GLOB.available_ui_styles[1]
if(istype(C))
if(!IsGuestKey(C.key))
@@ -208,17 +207,16 @@ GLOBAL_LIST_EMPTY(preferences_datums)
dat += "Age: [age]
"
dat += "Special Names:
"
- dat += "Backup Human Name: [custom_names["human"]] "
+ var/old_group
+ for(var/custom_name_id in GLOB.preferences_custom_names)
+ var/namedata = GLOB.preferences_custom_names[custom_name_id]
+ if(!old_group)
+ old_group = namedata["group"]
+ else if(old_group != namedata["group"])
+ old_group = namedata["group"]
+ dat += "
"
+ dat += "[namedata["pref_name"]]: [custom_names[custom_name_id]] "
dat += "
"
- dat += "Clown: [custom_names["clown"]] "
- dat += "Mime: [custom_names["mime"]]"
- dat += "
"
- dat += "AI: [custom_names["ai"]] "
- dat += "Cyborg: [custom_names["cyborg"]]"
- dat += "
"
- dat += "Chaplain religion: [custom_names["religion"]] "
- dat += "Chaplain deity: [custom_names["deity"]]
"
-
dat += "Custom job preferences:
"
dat += "Prefered security department: [prefered_security_department]
"
@@ -1066,6 +1064,11 @@ GLOBAL_LIST_EMPTY(preferences_datums)
random_character()
if("input")
+
+ if(href_list["preference"] in GLOB.preferences_custom_names)
+ ask_for_custom_name(user,href_list["preference"])
+
+
switch(href_list["preference"])
if("ghostform")
if(unlock_content)
@@ -1300,60 +1303,6 @@ GLOBAL_LIST_EMPTY(preferences_datums)
if(new_loc)
uplink_spawn_loc = new_loc
- if("human_name")
- var/new_human_name = reject_bad_name( input(user, "Choose your character's backup human name, used in the event you are assigned a command role as another species:", "Character Preference") as text|null )
- if(new_human_name)
- custom_names["human"] = new_human_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, -, ' and .")
-
- if("clown_name")
- var/new_clown_name = reject_bad_name( input(user, "Choose your character's clown name:", "Character Preference") as text|null )
- if(new_clown_name)
- custom_names["clown"] = new_clown_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, -, ' and .")
-
- if("mime_name")
- var/new_mime_name = reject_bad_name( input(user, "Choose your character's mime name:", "Character Preference") as text|null )
- if(new_mime_name)
- custom_names["mime"] = new_mime_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, -, ' and .")
-
- if("ai_name")
- var/new_ai_name = reject_bad_name( input(user, "Choose your character's AI name:", "Character Preference") as text|null, 1 )
- if(new_ai_name)
- custom_names["ai"] = new_ai_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, 0-9, -, ' and .")
-
- if("cyborg_name")
- var/raw_name = input(user, "Choose your character's cyborg name (Leave empty to use default naming scheme):", "Character Preference") as text|null
- var/new_cyborg_name
- if(!raw_name)
- new_cyborg_name = DEFAULT_CYBORG_NAME
- else
- new_cyborg_name = reject_bad_name(raw_name,1 )
- if(new_cyborg_name)
- custom_names["cyborg"] = new_cyborg_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, 0-9, -, ' and .")
-
- if("religion_name")
- var/new_religion_name = reject_bad_name( input(user, "Choose your character's religion:", "Character Preference") as text|null )
- if(new_religion_name)
- custom_names["religion"] = new_religion_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, -, ' and .")
-
- if("deity_name")
- var/new_deity_name = reject_bad_name( input(user, "Choose your character's deity:", "Character Preference") as text|null )
- if(new_deity_name)
- custom_names["deity"] = new_deity_name
- else
- to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z, -, ' and .")
-
if("sec_dept")
var/department = input(user, "Choose your prefered security department:", "Security Departments") as null|anything in GLOB.security_depts_prefs
if(department)
@@ -1572,3 +1521,36 @@ GLOBAL_LIST_EMPTY(preferences_datums)
character.update_body()
character.update_hair()
character.update_body_parts()
+
+/datum/preferences/proc/get_default_name(name_id)
+ switch(name_id)
+ if("human")
+ return random_unique_name()
+ if("ai")
+ return pick(GLOB.ai_names)
+ if("cyborg")
+ return DEFAULT_CYBORG_NAME
+ if("clown")
+ return pick(GLOB.clown_names)
+ if("mime")
+ return pick(GLOB.mime_names)
+ return random_unique_name()
+
+/datum/preferences/proc/ask_for_custom_name(mob/user,name_id)
+ var/namedata = GLOB.preferences_custom_names[name_id]
+ if(!namedata)
+ return
+
+ var/raw_name = input(user, "Choose your character's [namedata["qdesc"]]:","Character Preference") as text|null
+ if(!raw_name)
+ if(namedata["allow_null"])
+ custom_names[name_id] = get_default_name(name_id)
+ else
+ return
+ else
+ var/sanitized_name = reject_bad_name(raw_name,namedata["allow_numbers"])
+ if(!sanitized_name)
+ to_chat(user, "Invalid name. Your name should be at least 2 and at most [MAX_NAME_LEN] characters long. It may only contain the characters A-Z, a-z,[namedata["allow_numbers"] ? ",0-9," : ""] -, ' and .")
+ return
+ else
+ custom_names[name_id] = sanitized_name
\ No newline at end of file
diff --git a/code/modules/client/preferences_savefile.dm b/code/modules/client/preferences_savefile.dm
index e1a748b2cbf..36e8c36f08d 100644
--- a/code/modules/client/preferences_savefile.dm
+++ b/code/modules/client/preferences_savefile.dm
@@ -50,7 +50,6 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
if(current_version < 20)
pda_color = "#808000"
-
/datum/preferences/proc/load_path(ckey,filename="preferences.sav")
if(!ckey)
return
@@ -242,13 +241,12 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
else
S["feature_human_tail"] >> features["tail_human"]
S["feature_human_ears"] >> features["ears"]
- S["human_name"] >> custom_names["human"]
- S["clown_name"] >> custom_names["clown"]
- S["mime_name"] >> custom_names["mime"]
- S["ai_name"] >> custom_names["ai"]
- S["cyborg_name"] >> custom_names["cyborg"]
- S["religion_name"] >> custom_names["religion"]
- S["deity_name"] >> custom_names["deity"]
+
+ //Custom names
+ for(var/custom_name_id in GLOB.preferences_custom_names)
+ var/savefile_slot_name = custom_name_id + "_name" //TODO remove this
+ S[savefile_slot_name] >> custom_names[custom_name_id]
+
S["prefered_security_department"] >> prefered_security_department
//Jobs
@@ -274,14 +272,24 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
update_character(needs_update, S) //needs_update == savefile_version if we need an update (positive integer)
//Sanitize
- real_name = reject_bad_name(real_name)
- if(!features["mcolor"] || features["mcolor"] == "#000")
- features["mcolor"] = pick("FFFFFF","7F7F7F", "7FFF7F", "7F7FFF", "FF7F7F", "7FFFFF", "FF7FFF", "FFFF7F")
+
+ real_name = reject_bad_name(real_name)
+ gender = sanitize_gender(gender)
if(!real_name)
real_name = random_unique_name(gender)
+
+ for(var/custom_name_id in GLOB.preferences_custom_names)
+ var/namedata = GLOB.preferences_custom_names[custom_name_id]
+ custom_names[custom_name_id] = reject_bad_name(custom_names[custom_name_id],namedata["allow_numbers"])
+ if(!custom_names[custom_name_id])
+ custom_names[custom_name_id] = get_default_name(custom_name_id)
+
+ if(!features["mcolor"] || features["mcolor"] == "#000")
+ features["mcolor"] = pick("FFFFFF","7F7F7F", "7FFF7F", "7F7FFF", "FF7F7F", "7FFFFF", "FF7FFF", "FFFF7F")
+
be_random_name = sanitize_integer(be_random_name, 0, 1, initial(be_random_name))
be_random_body = sanitize_integer(be_random_body, 0, 1, initial(be_random_body))
- gender = sanitize_gender(gender)
+
if(gender == MALE)
hair_style = sanitize_inlist(hair_style, GLOB.hair_styles_male_list)
facial_hair_style = sanitize_inlist(facial_hair_style, GLOB.facial_hair_styles_male_list)
@@ -369,13 +377,12 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
WRITE_FILE(S["feature_lizard_body_markings"] , features["body_markings"])
WRITE_FILE(S["feature_lizard_legs"] , features["legs"])
WRITE_FILE(S["feature_moth_wings"] , features["moth_wings"])
- WRITE_FILE(S["human_name"] , custom_names["human"])
- WRITE_FILE(S["clown_name"] , custom_names["clown"])
- WRITE_FILE(S["mime_name"] , custom_names["mime"])
- WRITE_FILE(S["ai_name"] , custom_names["ai"])
- WRITE_FILE(S["cyborg_name"] , custom_names["cyborg"])
- WRITE_FILE(S["religion_name"] , custom_names["religion"])
- WRITE_FILE(S["deity_name"] , custom_names["deity"])
+
+ //Custom names
+ for(var/custom_name_id in GLOB.preferences_custom_names)
+ var/savefile_slot_name = custom_name_id + "_name" //TODO remove this
+ WRITE_FILE(S[savefile_slot_name],custom_names[custom_name_id])
+
WRITE_FILE(S["prefered_security_department"] , prefered_security_department)
//Jobs