diff --git a/code/__HELPERS/game.dm b/code/__HELPERS/game.dm
index 8a19ab1aeb6..3e186b19df5 100644
--- a/code/__HELPERS/game.dm
+++ b/code/__HELPERS/game.dm
@@ -332,7 +332,7 @@ var/list/DummyCache = list()
return 1
// Comment out when done testing shit.
-#define DEBUG_ROLESELECT
+//#define DEBUG_ROLESELECT
#ifdef DEBUG_ROLESELECT
# define roleselect_debug(x) testing(x)
@@ -352,7 +352,7 @@ var/list/DummyCache = list()
roleselect_debug("get_active_candidates(role_id=[role_id], buffer=[buffer], poll=[poll]): Skipping [G] - Shitty candidate.")
continue
- if(!G.client.desires_role(role_id,display_to_user=(poll && i==0))) // Only ask once.
+ if(!G.client.desires_role(role_id,display_to_user=(poll!=0 && i==0) ? poll : 0)) // Only ask once.
roleselect_debug("get_active_candidates(role_id=[role_id], buffer=[buffer], poll=[poll]): Skipping [G] - Doesn't want role.")
continue
diff --git a/code/modules/client/client procs.dm b/code/modules/client/client procs.dm
index 86356183382..c34e5ad93e4 100644
--- a/code/modules/client/client procs.dm
+++ b/code/modules/client/client procs.dm
@@ -308,18 +308,34 @@
/proc/get_role_desire_str(var/rolepref)
- if((rolepref & (ROLEPREF_ENABLE|ROLEPREF_PERSIST)) == ROLEPREF_PERSIST)
- return "Never"
- if((rolepref & (ROLEPREF_ENABLE|ROLEPREF_PERSIST)) == 0)
- return "No"
- if((rolepref & (ROLEPREF_ENABLE|ROLEPREF_PERSIST)) == ROLEPREF_ENABLE)
- return "Yes"
- if((rolepref & (ROLEPREF_ENABLE|ROLEPREF_PERSIST)) == (ROLEPREF_ENABLE|ROLEPREF_PERSIST))
- return "Always"
+ switch(rolepref & ROLEPREF_VALMASK)
+ if(ROLEPREF_NEVER)
+ return "Never"
+ if(ROLEPREF_NO)
+ return "No"
+ if(ROLEPREF_YES)
+ return "Yes"
+ if(ROLEPREF_ALWAYS)
+ return "Always"
return "???"
/client/proc/desires_role(var/role_id, var/display_to_user=0)
var/role_desired = prefs.roles[role_id]
- if(display_to_user)
- src << "The game is currently looking for [role_id] candidates. Your current answer is [get_role_desire_str(role_desired)]."
+ if(display_to_user && !(role_desired & ROLEPREF_PERSIST))
+ if(!(role_desired & ROLEPREF_POLLED))
+ spawn
+ var/answer = alert(src,"[display_to_user]\n\nNOTE: You will only be polled about this role once per round. To change your choice, use Preferences > Setup Special Roles. The change will take place AFTER this recruiting period.","Role Recruitment", "Yes","No","Never")
+ switch(answer)
+ if("Never")
+ prefs.roles[role_id] = ROLEPREF_NEVER
+ if("No")
+ prefs.roles[role_id] = ROLEPREF_NO
+ if("Yes")
+ prefs.roles[role_id] = ROLEPREF_YES
+ //if("Always")
+ // prefs.roles[role_id] = ROLEPREF_ALWAYS
+ //testing("Client [src] answered [answer] to [role_id] poll.")
+ prefs.roles[role_id] |= ROLEPREF_POLLED
+ else
+ src << "The game is currently looking for [role_id] candidates. Your current answer is [get_role_desire_str(role_desired)]."
return role_desired & ROLEPREF_ENABLE
\ No newline at end of file
diff --git a/code/modules/client/preferences.dm b/code/modules/client/preferences.dm
index 276ba094d3f..9131da8efba 100644
--- a/code/modules/client/preferences.dm
+++ b/code/modules/client/preferences.dm
@@ -710,6 +710,40 @@ var/const/MAX_SAVE_SLOTS = 8
roles[role_id] ^= ROLEPREF_ENABLE
return 1
+ proc/SetRole(var/mob/user, var/list/href_list)
+ var/role_id = href_list["role_id"]
+ //user << "Toggling role [role_id] (currently at [roles[role_id]])..."
+ if(!(role_id in special_roles))
+ user << "BUG: Unable to find role [role_id]."
+ return 0
+
+ if(roles[role_id] == null || roles[role_id] == "")
+ roles[role_id] = 0
+
+ var/question={"Would you like to be \a [role_id] this round?
+
+No/Yes: Only affects this round.
+Never/Always: Saved for later rounds.
+
+NOTE: The change will take effect AFTER any current recruiting periods."}
+ var/answer = alert(question,"Role Preference", "Never", "No", "Yes", "Always")
+ var/newval=0
+ switch(answer)
+ if("Never")
+ newval = ROLEPREF_NEVER
+ if("No")
+ newval = ROLEPREF_NO
+ if("Yes")
+ newval = ROLEPREF_YES
+ if("Always")
+ newval = ROLEPREF_ALWAYS
+ roles[role_id] = (roles[role_id] & ~ROLEPREF_VALMASK) | newval // We only set the lower 2 bits, leaving polled and friends untouched.
+
+ save_preferences_sqlite(user, user.ckey)
+ save_character_sqlite(user.ckey, user, default_slot)
+
+ return 1
+
proc/process_link(mob/user, list/href_list)
if(!user)
return
@@ -1431,3 +1465,5 @@ var/const/MAX_SAVE_SLOTS = 8
switch(href_list["preference"])
if("set_roles")
return SetRoles(usr, href_list)
+ if("set_role")
+ return SetRole(usr, href_list)
diff --git a/code/modules/client/preferences_savefile.dm b/code/modules/client/preferences_savefile.dm
index c1c3ad485a0..db1ff1ace0c 100644
--- a/code/modules/client/preferences_savefile.dm
+++ b/code/modules/client/preferences_savefile.dm
@@ -720,7 +720,7 @@ AND players.player_slot = ? ;"}, ckey, slot)
if(!(roles[role_id] & ROLEPREF_PERSIST))
continue
q = new
- q.Add("INSERT INTO client_roles (ckey, slot, role, preference) VALUES (?,?,?,?)", ckey, slot, role_id, (roles[role_id] & ~ROLEPREF_PERSIST))
+ q.Add("INSERT INTO client_roles (ckey, slot, role, preference) VALUES (?,?,?,?)", ckey, slot, role_id, (roles[role_id] & ROLEPREF_SAVEMASK))
if(!q.Execute(db))
message_admins("Error #: [q.Error()] - [q.ErrorMsg()]")
warning("Error #:[q.Error()] - [q.ErrorMsg()]")
diff --git a/code/modules/mob/living/simple_animal/borer.dm b/code/modules/mob/living/simple_animal/borer.dm
index aea8b03822d..94d038a1896 100644
--- a/code/modules/mob/living/simple_animal/borer.dm
+++ b/code/modules/mob/living/simple_animal/borer.dm
@@ -397,18 +397,18 @@ mob/living/simple_animal/borer/proc/detach()
//Procs for grabbing players.
mob/living/simple_animal/borer/proc/request_player()
var/list/candidates=list()
- testing("Polling for borers.")
+ //testing("Polling for borers.")
for(var/mob/dead/observer/G in get_active_candidates(ROLE_BORER, poll="HEY KID, YOU WANNA BE A BORER?"))
if(!G.client)
- testing("Client of [G] inexistent")
+ //testing("Client of [G] inexistent")
continue
if(G.client.holder)
- testing("Client of [G] is admin.")
+ //testing("Client of [G] is admin.")
continue
if(jobban_isbanned(G, "Syndicate"))
- testing("Jobbanned.")
+ //testing("[G] is jobbanned.")
continue
candidates += G
diff --git a/code/setup.dm b/code/setup.dm
index 355f00838c4..296040a738a 100644
--- a/code/setup.dm
+++ b/code/setup.dm
@@ -707,10 +707,20 @@ var/list/TAGGERLOCATIONS = list(
//////////////////////////////////
// First bit is no/yes.
// Second bit is persistence (save to char prefs).
+// Third bit is whether we polled for that role yet.
#define ROLEPREF_ENABLE 1 // Enable role for this character.
#define ROLEPREF_PERSIST 2 // Save preference.
#define ROLEPREF_POLLED 4 // Have we polled this guy?
+#define ROLEPREF_NEVER ROLEPREF_PERSIST
+#define ROLEPREF_NO 0
+#define ROLEPREF_YES ROLEPREF_ENABLE
+#define ROLEPREF_ALWAYS (ROLEPREF_ENABLE|ROLEPREF_PERSIST)
+
+// Masks.
+#define ROLEPREF_SAVEMASK 1 // 0b00000001 - For saving shit.
+#define ROLEPREF_VALMASK 3 // 0b00000011 - For a lot of things.
+
// Should correspond to jobbans, too.
#define ROLE_ALIEN "alien"
#define ROLE_BLOB "blob" // New!