mirror of
https://github.com/Yawn-Wider/YWPolarisVore.git
synced 2026-08-23 21:17:20 +01:00
Merge branch 'release' of https://github.com/VOREStation/VOREStation into upstream-update
This commit is contained in:
@@ -1,481 +1,481 @@
|
||||
|
||||
//Either pass the mob you wish to ban in the 'banned_mob' attribute, or the banckey, banip and bancid variables. If both are passed, the mob takes priority! If a mob is not passed, banckey is the minimum that needs to be passed! banip and bancid are optional.
|
||||
/datum/admins/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration = -1, var/reason, var/job = "", var/rounds = 0, var/banckey = null, var/banip = null, var/bancid = null)
|
||||
|
||||
if(!check_rights(R_MOD,0) && !check_rights(R_BAN)) return
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
return
|
||||
|
||||
var/serverip = "[world.internet_address]:[world.port]"
|
||||
var/bantype_pass = 0
|
||||
var/bantype_str
|
||||
switch(bantype)
|
||||
if(BANTYPE_PERMA)
|
||||
bantype_str = "PERMABAN"
|
||||
duration = -1
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_TEMP)
|
||||
bantype_str = "TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_PERMA)
|
||||
bantype_str = "JOB_PERMABAN"
|
||||
duration = -1
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_TEMP)
|
||||
bantype_str = "JOB_TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if( !bantype_pass ) return
|
||||
if( !istext(reason) ) return
|
||||
if( !isnum(duration) ) return
|
||||
|
||||
var/ckey
|
||||
var/computerid
|
||||
var/ip
|
||||
|
||||
if(ismob(banned_mob))
|
||||
ckey = banned_mob.ckey
|
||||
if(banned_mob.client)
|
||||
computerid = banned_mob.client.computer_id
|
||||
ip = banned_mob.client.address
|
||||
else if(banckey)
|
||||
ckey = ckey(banckey)
|
||||
computerid = bancid
|
||||
ip = banip
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT id FROM erro_player WHERE ckey = '[ckey]'")
|
||||
query.Execute()
|
||||
var/validckey = 0
|
||||
if(query.NextRow())
|
||||
validckey = 1
|
||||
if(!validckey)
|
||||
if(!banned_mob || (banned_mob && !IsGuestKey(banned_mob.key))) //VOREStation Edit Start.
|
||||
var/confirm = tgui_alert(usr, "This ckey hasn't been seen, are you sure?", "Confirm Badmin", list("Yes", "No"))
|
||||
if(confirm == "No")
|
||||
return //VOREStation Edit End
|
||||
|
||||
var/a_ckey
|
||||
var/a_computerid
|
||||
var/a_ip
|
||||
|
||||
if(src.owner && istype(src.owner, /client))
|
||||
a_ckey = src.owner:ckey
|
||||
a_computerid = src.owner:computer_id
|
||||
a_ip = src.owner:address
|
||||
|
||||
var/who
|
||||
for(var/client/C in GLOB.clients)
|
||||
if(!who)
|
||||
who = "[C]"
|
||||
else
|
||||
who += ", [C]"
|
||||
|
||||
var/adminwho
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(!adminwho)
|
||||
adminwho = "[C]"
|
||||
else
|
||||
adminwho += ", [C]"
|
||||
|
||||
reason = sql_sanitize_text(reason)
|
||||
|
||||
var/sql = "INSERT INTO erro_ban (`id`,`bantime`,`serverip`,`bantype`,`reason`,`job`,`duration`,`rounds`,`expiration_time`,`ckey`,`computerid`,`ip`,`a_ckey`,`a_computerid`,`a_ip`,`who`,`adminwho`,`edits`,`unbanned`,`unbanned_datetime`,`unbanned_ckey`,`unbanned_computerid`,`unbanned_ip`) VALUES (null, Now(), '[serverip]', '[bantype_str]', '[reason]', '[job]', [(duration)?"[duration]":"0"], [(rounds)?"[rounds]":"0"], Now() + INTERVAL [(duration>0) ? duration : 0] MINUTE, '[ckey]', '[computerid]', '[ip]', '[a_ckey]', '[a_computerid]', '[a_ip]', '[who]', '[adminwho]', '', null, null, null, null, null)"
|
||||
var/DBQuery/query_insert = dbcon.NewQuery(sql)
|
||||
query_insert.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Ban saved to database.")]</span>")
|
||||
message_admins("[key_name_admin(usr)] has added a [bantype_str] for [ckey] [(job)?"([job])":""] [(duration > 0)?"([duration] minutes)":""] with the reason: \"[reason]\" to the ban database.",1)
|
||||
|
||||
|
||||
|
||||
/datum/admins/proc/DB_ban_unban(var/ckey, var/bantype, var/job = "")
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
var/bantype_str
|
||||
if(bantype)
|
||||
var/bantype_pass = 0
|
||||
switch(bantype)
|
||||
if(BANTYPE_PERMA)
|
||||
bantype_str = "PERMABAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_TEMP)
|
||||
bantype_str = "TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_PERMA)
|
||||
bantype_str = "JOB_PERMABAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_TEMP)
|
||||
bantype_str = "JOB_TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_ANY_FULLBAN)
|
||||
bantype_str = "ANY"
|
||||
bantype_pass = 1
|
||||
if( !bantype_pass ) return
|
||||
|
||||
var/bantype_sql
|
||||
if(bantype_str == "ANY")
|
||||
bantype_sql = "(bantype = 'PERMABAN' OR (bantype = 'TEMPBAN' AND expiration_time > Now() ) )"
|
||||
else
|
||||
bantype_sql = "bantype = '[bantype_str]'"
|
||||
|
||||
var/sql = "SELECT id FROM erro_ban WHERE ckey = '[ckey]' AND [bantype_sql] AND (unbanned is null OR unbanned = false)"
|
||||
if(job)
|
||||
sql += " AND job = '[job]'"
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
return
|
||||
|
||||
var/ban_id
|
||||
var/ban_number = 0 //failsafe
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery(sql)
|
||||
query.Execute()
|
||||
while(query.NextRow())
|
||||
ban_id = query.item[1]
|
||||
ban_number++;
|
||||
|
||||
if(ban_number == 0)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to no bans fitting the search criteria. If this is not a legacy ban you should contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
if(ban_number > 1)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to multiple bans fitting the search criteria. Note down the ckey, job and current time and contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
if(istext(ban_id))
|
||||
ban_id = text2num(ban_id)
|
||||
if(!isnum(ban_id))
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to a ban ID mismatch. Contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
DB_ban_unban_by_id(ban_id)
|
||||
|
||||
/datum/admins/proc/DB_ban_edit(var/banid = null, var/param = null)
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
if(!isnum(banid) || !istext(param))
|
||||
to_chat(usr, "Cancelled")
|
||||
return
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT ckey, duration, reason FROM erro_ban WHERE id = [banid]")
|
||||
query.Execute()
|
||||
|
||||
var/eckey = usr.ckey //Editing admin ckey
|
||||
var/pckey //(banned) Player ckey
|
||||
var/duration //Old duration
|
||||
var/reason //Old reason
|
||||
|
||||
if(query.NextRow())
|
||||
pckey = query.item[1]
|
||||
duration = query.item[2]
|
||||
reason = query.item[3]
|
||||
else
|
||||
to_chat(usr, "<span class='filter_adminlog'>Invalid ban id. Contact the database admin</span>")
|
||||
return
|
||||
|
||||
reason = sql_sanitize_text(reason)
|
||||
var/value
|
||||
|
||||
switch(param)
|
||||
if("reason")
|
||||
if(!value)
|
||||
value = sanitize(tgui_input_text(usr, "Insert the new reason for [pckey]'s ban", "New Reason", "[reason]", null))
|
||||
value = sql_sanitize_text(value)
|
||||
if(!value)
|
||||
to_chat(usr, "Cancelled")
|
||||
return
|
||||
|
||||
var/DBQuery/update_query = dbcon.NewQuery("UPDATE erro_ban SET reason = '[value]', edits = CONCAT(edits,'- [eckey] changed ban reason from <cite><b>\\\"[reason]\\\"</b></cite> to <cite><b>\\\"[value]\\\"</b></cite><BR>') WHERE id = [banid]")
|
||||
update_query.Execute()
|
||||
message_admins("[key_name_admin(usr)] has edited a ban for [pckey]'s reason from [reason] to [value]",1)
|
||||
if("duration")
|
||||
if(!value)
|
||||
value = tgui_input_number(usr, "Insert the new duration (in minutes) for [pckey]'s ban", "New Duration", "[duration]", null)
|
||||
if(!isnum(value) || !value)
|
||||
to_chat(usr, "Cancelled")
|
||||
return
|
||||
|
||||
var/DBQuery/update_query = dbcon.NewQuery("UPDATE erro_ban SET duration = [value], edits = CONCAT(edits,'- [eckey] changed ban duration from [duration] to [value]<br>'), expiration_time = DATE_ADD(bantime, INTERVAL [value] MINUTE) WHERE id = [banid]")
|
||||
message_admins("[key_name_admin(usr)] has edited a ban for [pckey]'s duration from [duration] to [value]",1)
|
||||
update_query.Execute()
|
||||
if("unban")
|
||||
if(tgui_alert(usr, "Unban [pckey]?", "Unban?", list("Yes", "No")) == "Yes")
|
||||
DB_ban_unban_by_id(banid)
|
||||
return
|
||||
to_chat(usr, "<span class='filter_adminlog'>Cancelled</span>")
|
||||
return
|
||||
|
||||
/datum/admins/proc/DB_ban_unban_by_id(var/id)
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
var/sql = "SELECT ckey FROM erro_ban WHERE id = [id]"
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
return
|
||||
|
||||
var/ban_number = 0 //failsafe
|
||||
|
||||
var/pckey
|
||||
var/DBQuery/query = dbcon.NewQuery(sql)
|
||||
query.Execute()
|
||||
while(query.NextRow())
|
||||
pckey = query.item[1]
|
||||
ban_number++;
|
||||
|
||||
if(ban_number == 0)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to a ban id not being present in the database.")]</span>")
|
||||
return
|
||||
|
||||
if(ban_number > 1)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to multiple bans having the same ID. Contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
if(!src.owner || !istype(src.owner, /client))
|
||||
return
|
||||
|
||||
var/unban_ckey = src.owner:ckey
|
||||
var/unban_computerid = src.owner:computer_id
|
||||
var/unban_ip = src.owner:address
|
||||
|
||||
var/sql_update = "UPDATE erro_ban SET unbanned = 1, unbanned_datetime = Now(), unbanned_ckey = '[unban_ckey]', unbanned_computerid = '[unban_computerid]', unbanned_ip = '[unban_ip]' WHERE id = [id]"
|
||||
message_admins("[key_name_admin(usr)] has lifted [pckey]'s ban.",1)
|
||||
|
||||
var/DBQuery/query_update = dbcon.NewQuery(sql_update)
|
||||
query_update.Execute()
|
||||
|
||||
|
||||
/client/proc/DB_ban_panel()
|
||||
set category = "Admin"
|
||||
set name = "Banning Panel"
|
||||
set desc = "Edit admin permissions"
|
||||
|
||||
if(!holder)
|
||||
return
|
||||
|
||||
holder.DB_ban_panel()
|
||||
|
||||
|
||||
/datum/admins/proc/DB_ban_panel(var/playerckey = null, var/adminckey = null, var/playerip = null, var/playercid = null, var/dbbantype = null, var/match = null)
|
||||
if(!usr.client)
|
||||
return
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Failed to establish database connection")]</span>")
|
||||
return
|
||||
|
||||
var/output = "<div align='center'><table width='90%'><tr>"
|
||||
|
||||
output += "<td width='35%' align='center'>"
|
||||
output += "<h1>Banning panel</h1>"
|
||||
output += "</td>"
|
||||
|
||||
output += "<td width='65%' align='center' bgcolor='#f9f9f9'>"
|
||||
|
||||
output += "<form method='GET' action='?src=\ref[src]'>[HrefTokenFormField()]"
|
||||
output += "<b>Add custom ban:</b> (ONLY use this if you can't ban through any other method)"
|
||||
output += "<input type='hidden' name='src' value='\ref[src]'>"
|
||||
output += "<table width='100%'><tr>"
|
||||
output += "<td width='50%' align='right'><b>Ban type:</b><select name='dbbanaddtype'>"
|
||||
output += "<option value=''>--</option>"
|
||||
output += "<option value='[BANTYPE_PERMA]'>PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_TEMP]'>TEMPBAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_PERMA]'>JOB PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_TEMP]'>JOB TEMPBAN</option>"
|
||||
output += "</select></td>"
|
||||
output += "<td width='50%' align='right'><b>Ckey:</b> <input type='text' name='dbbanaddckey'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>IP:</b> <input type='text' name='dbbanaddip'></td>"
|
||||
output += "<td width='50%' align='right'><b>CID:</b> <input type='text' name='dbbanaddcid'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>Duration:</b> <input type='text' name='dbbaddduration'></td>"
|
||||
output += "<td width='50%' align='right'><b>Job:</b><select name='dbbanaddjob'>"
|
||||
output += "<option value=''>--</option>"
|
||||
for(var/j in get_all_jobs())
|
||||
output += "<option value='[j]'>[j]</option>"
|
||||
for(var/j in SSjob.get_job_titles_in_department(DEPARTMENT_SYNTHETIC))
|
||||
output += "<option value='[j]'>[j]</option>"
|
||||
var/list/bantypes = list("traitor","changeling","operative","revolutionary","cultist","wizard") //For legacy bans.
|
||||
for(var/antag_type in all_antag_types) // Grab other bans.
|
||||
var/datum/antagonist/antag = all_antag_types[antag_type]
|
||||
bantypes |= antag.bantype
|
||||
for(var/j in bantypes)
|
||||
output += "<option value='[j]'>[j]</option>"
|
||||
output += "</select></td></tr></table>"
|
||||
output += "<b>Reason:<br></b><textarea name='dbbanreason' cols='50'></textarea><br>"
|
||||
output += "<input type='submit' value='Add ban'>"
|
||||
output += "</form>"
|
||||
|
||||
output += "</td>"
|
||||
output += "</tr>"
|
||||
output += "</table>"
|
||||
|
||||
output += "<form method='GET' action='?src=\ref[src]'>[HrefTokenFormField()]"
|
||||
output += "<table width='60%'><tr><td colspan='2' align='left'><b>Search:</b>"
|
||||
output += "<input type='hidden' name='src' value='\ref[src]'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>Ckey:</b> <input type='text' name='dbsearchckey' value='[playerckey]'></td>"
|
||||
output += "<td width='50%' align='right'><b>Admin ckey:</b> <input type='text' name='dbsearchadmin' value='[adminckey]'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>IP:</b> <input type='text' name='dbsearchip' value='[playerip]'></td>"
|
||||
output += "<td width='50%' align='right'><b>CID:</b> <input type='text' name='dbsearchcid' value='[playercid]'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right' colspan='2'><b>Ban type:</b><select name='dbsearchbantype'>"
|
||||
output += "<option value=''>--</option>"
|
||||
output += "<option value='[BANTYPE_PERMA]'>PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_TEMP]'>TEMPBAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_PERMA]'>JOB PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_TEMP]'>JOB TEMPBAN</option>"
|
||||
output += "</select></td></tr></table>"
|
||||
output += "<br><input type='submit' value='search'><br>"
|
||||
output += "<input type='checkbox' value='[match]' name='dbmatch' [match? "checked=\"1\"" : null]> Match(min. 3 characters to search by key or ip, and 7 to search by cid)<br>"
|
||||
output += "</form>"
|
||||
output += "Please note that all jobban bans or unbans are in-effect the following round.<br>"
|
||||
output += "This search shows only last 100 bans."
|
||||
|
||||
if(adminckey || playerckey || playerip || playercid || dbbantype)
|
||||
|
||||
adminckey = ckey(adminckey)
|
||||
playerckey = ckey(playerckey)
|
||||
playerip = sql_sanitize_text(playerip)
|
||||
playercid = sql_sanitize_text(playercid)
|
||||
|
||||
if(adminckey || playerckey || playerip || playercid || dbbantype)
|
||||
|
||||
var/blcolor = "#ffeeee" //banned light
|
||||
var/bdcolor = "#ffdddd" //banned dark
|
||||
var/ulcolor = "#eeffee" //unbanned light
|
||||
var/udcolor = "#ddffdd" //unbanned dark
|
||||
var/alcolor = "#eeeeff" // auto-unbanned light
|
||||
var/adcolor = "#ddddff" // auto-unbanned dark
|
||||
|
||||
output += "<table width='90%' bgcolor='#e3e3e3' cellpadding='5' cellspacing='0' align='center'>"
|
||||
output += "<tr>"
|
||||
output += "<th width='25%'><b>TYPE</b></th>"
|
||||
output += "<th width='20%'><b>CKEY</b></th>"
|
||||
output += "<th width='20%'><b>TIME APPLIED</b></th>"
|
||||
output += "<th width='20%'><b>ADMIN</b></th>"
|
||||
output += "<th width='15%'><b>OPTIONS</b></th>"
|
||||
output += "</tr>"
|
||||
|
||||
var/adminsearch = ""
|
||||
var/playersearch = ""
|
||||
var/ipsearch = ""
|
||||
var/cidsearch = ""
|
||||
var/bantypesearch = ""
|
||||
|
||||
if(!match)
|
||||
if(adminckey)
|
||||
adminsearch = "AND a_ckey = '[adminckey]' "
|
||||
if(playerckey)
|
||||
playersearch = "AND ckey = '[playerckey]' "
|
||||
if(playerip)
|
||||
ipsearch = "AND ip = '[playerip]' "
|
||||
if(playercid)
|
||||
cidsearch = "AND computerid = '[playercid]' "
|
||||
else
|
||||
if(adminckey && length(adminckey) >= 3)
|
||||
adminsearch = "AND a_ckey LIKE '[adminckey]%' "
|
||||
if(playerckey && length(playerckey) >= 3)
|
||||
playersearch = "AND ckey LIKE '[playerckey]%' "
|
||||
if(playerip && length(playerip) >= 3)
|
||||
ipsearch = "AND ip LIKE '[playerip]%' "
|
||||
if(playercid && length(playercid) >= 7)
|
||||
cidsearch = "AND computerid LIKE '[playercid]%' "
|
||||
|
||||
if(dbbantype)
|
||||
bantypesearch = "AND bantype = "
|
||||
|
||||
switch(dbbantype)
|
||||
if(BANTYPE_TEMP)
|
||||
bantypesearch += "'TEMPBAN' "
|
||||
if(BANTYPE_JOB_PERMA)
|
||||
bantypesearch += "'JOB_PERMABAN' "
|
||||
if(BANTYPE_JOB_TEMP)
|
||||
bantypesearch += "'JOB_TEMPBAN' "
|
||||
else
|
||||
bantypesearch += "'PERMABAN' "
|
||||
|
||||
var/DBQuery/select_query = dbcon.NewQuery("SELECT id, bantime, bantype, reason, job, duration, expiration_time, ckey, a_ckey, unbanned, unbanned_ckey, unbanned_datetime, edits, ip, computerid FROM erro_ban WHERE 1 [playersearch] [adminsearch] [ipsearch] [cidsearch] [bantypesearch] ORDER BY bantime DESC LIMIT 100")
|
||||
select_query.Execute()
|
||||
|
||||
var/now = time2text(world.realtime, "YYYY-MM-DD hh:mm:ss") // MUST BE the same format as SQL gives us the dates in, and MUST be least to most specific (i.e. year, month, day not day, month, year)
|
||||
|
||||
while(select_query.NextRow())
|
||||
var/banid = select_query.item[1]
|
||||
var/bantime = select_query.item[2]
|
||||
var/bantype = select_query.item[3]
|
||||
var/reason = select_query.item[4]
|
||||
var/job = select_query.item[5]
|
||||
var/duration = select_query.item[6]
|
||||
var/expiration = select_query.item[7]
|
||||
var/ckey = select_query.item[8]
|
||||
var/ackey = select_query.item[9]
|
||||
var/unbanned = select_query.item[10]
|
||||
var/unbanckey = select_query.item[11]
|
||||
var/unbantime = select_query.item[12]
|
||||
var/edits = select_query.item[13]
|
||||
var/ip = select_query.item[14]
|
||||
var/cid = select_query.item[15]
|
||||
|
||||
// true if this ban has expired
|
||||
var/auto = (bantype in list("TEMPBAN", "JOB_TEMPBAN")) && now > expiration // oh how I love ISO 8601 (ish) date strings
|
||||
|
||||
var/lcolor = blcolor
|
||||
var/dcolor = bdcolor
|
||||
if(unbanned)
|
||||
lcolor = ulcolor
|
||||
dcolor = udcolor
|
||||
else if(auto)
|
||||
lcolor = alcolor
|
||||
dcolor = adcolor
|
||||
|
||||
var/typedesc =""
|
||||
switch(bantype)
|
||||
if("PERMABAN")
|
||||
typedesc = "<font color='red'><b>PERMABAN</b></font>"
|
||||
if("TEMPBAN")
|
||||
typedesc = "<b>TEMPBAN</b><br><font size='2'>([duration] minutes) [(unbanned || auto) ? "" : "(<a href=\"byond://?src=\ref[src];[HrefToken()];dbbanedit=duration;dbbanid=[banid]\">Edit</a>)"]<br>Expires [expiration]</font>"
|
||||
if("JOB_PERMABAN")
|
||||
typedesc = "<b>JOBBAN</b><br><font size='2'>([job])</font>"
|
||||
if("JOB_TEMPBAN")
|
||||
typedesc = "<b>TEMP JOBBAN</b><br><font size='2'>([job])<br>([duration] minutes<br>Expires [expiration]</font>"
|
||||
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center'>[typedesc]</td>"
|
||||
output += "<td align='center'><b>[ckey]</b></td>"
|
||||
output += "<td align='center'>[bantime]</td>"
|
||||
output += "<td align='center'><b>[ackey]</b></td>"
|
||||
output += "<td align='center'>[(unbanned || auto) ? "" : "<b><a href=\"byond://?src=\ref[src];[HrefToken()];dbbanedit=unban;dbbanid=[banid]\">Unban</a></b>"]</td>"
|
||||
output += "</tr>"
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='2' bgcolor=''><b>IP:</b> [ip]</td>"
|
||||
output += "<td align='center' colspan='3' bgcolor=''><b>CIP:</b> [cid]</td>"
|
||||
output += "</tr>"
|
||||
output += "<tr bgcolor='[lcolor]'>"
|
||||
output += "<td align='center' colspan='5'><b>Reason: [(unbanned || auto) ? "" : "(<a href=\"byond://?src=\ref[src];[HrefToken()];dbbanedit=reason;dbbanid=[banid]\">Edit</a>)"]</b> <cite>\"[reason]\"</cite></td>"
|
||||
output += "</tr>"
|
||||
if(edits)
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='5'><b>EDITS</b></td>"
|
||||
output += "</tr>"
|
||||
output += "<tr bgcolor='[lcolor]'>"
|
||||
output += "<td align='center' colspan='5'><font size='2'>[edits]</font></td>"
|
||||
output += "</tr>"
|
||||
if(unbanned)
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='5' bgcolor=''><b>UNBANNED by admin [unbanckey] on [unbantime]</b></td>"
|
||||
output += "</tr>"
|
||||
else if(auto)
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='5' bgcolor=''><b>EXPIRED at [expiration]</b></td>"
|
||||
output += "</tr>"
|
||||
output += "<tr>"
|
||||
output += "<td colspan='5' bgcolor='white'> </td>"
|
||||
output += "</tr>"
|
||||
|
||||
output += "</table></div>"
|
||||
|
||||
usr << browse(output,"window=lookupbans;size=900x700")
|
||||
|
||||
//Either pass the mob you wish to ban in the 'banned_mob' attribute, or the banckey, banip and bancid variables. If both are passed, the mob takes priority! If a mob is not passed, banckey is the minimum that needs to be passed! banip and bancid are optional.
|
||||
/datum/admins/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration = -1, var/reason, var/job = "", var/rounds = 0, var/banckey = null, var/banip = null, var/bancid = null)
|
||||
|
||||
if(!check_rights(R_MOD,0) && !check_rights(R_BAN)) return
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
return
|
||||
|
||||
var/serverip = "[world.internet_address]:[world.port]"
|
||||
var/bantype_pass = 0
|
||||
var/bantype_str
|
||||
switch(bantype)
|
||||
if(BANTYPE_PERMA)
|
||||
bantype_str = "PERMABAN"
|
||||
duration = -1
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_TEMP)
|
||||
bantype_str = "TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_PERMA)
|
||||
bantype_str = "JOB_PERMABAN"
|
||||
duration = -1
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_TEMP)
|
||||
bantype_str = "JOB_TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if( !bantype_pass ) return
|
||||
if( !istext(reason) ) return
|
||||
if( !isnum(duration) ) return
|
||||
|
||||
var/ckey
|
||||
var/computerid
|
||||
var/ip
|
||||
|
||||
if(ismob(banned_mob))
|
||||
ckey = banned_mob.ckey
|
||||
if(banned_mob.client)
|
||||
computerid = banned_mob.client.computer_id
|
||||
ip = banned_mob.client.address
|
||||
else if(banckey)
|
||||
ckey = ckey(banckey)
|
||||
computerid = bancid
|
||||
ip = banip
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT id FROM erro_player WHERE ckey = '[ckey]'")
|
||||
query.Execute()
|
||||
var/validckey = 0
|
||||
if(query.NextRow())
|
||||
validckey = 1
|
||||
if(!validckey)
|
||||
if(!banned_mob || (banned_mob && !IsGuestKey(banned_mob.key))) //VOREStation Edit Start.
|
||||
var/confirm = tgui_alert(usr, "This ckey hasn't been seen, are you sure?", "Confirm Badmin", list("Yes", "No"))
|
||||
if(confirm == "No")
|
||||
return //VOREStation Edit End
|
||||
|
||||
var/a_ckey
|
||||
var/a_computerid
|
||||
var/a_ip
|
||||
|
||||
if(src.owner && istype(src.owner, /client))
|
||||
a_ckey = src.owner:ckey
|
||||
a_computerid = src.owner:computer_id
|
||||
a_ip = src.owner:address
|
||||
|
||||
var/who
|
||||
for(var/client/C in GLOB.clients)
|
||||
if(!who)
|
||||
who = "[C]"
|
||||
else
|
||||
who += ", [C]"
|
||||
|
||||
var/adminwho
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(!adminwho)
|
||||
adminwho = "[C]"
|
||||
else
|
||||
adminwho += ", [C]"
|
||||
|
||||
reason = sql_sanitize_text(reason)
|
||||
|
||||
var/sql = "INSERT INTO erro_ban (`id`,`bantime`,`serverip`,`bantype`,`reason`,`job`,`duration`,`rounds`,`expiration_time`,`ckey`,`computerid`,`ip`,`a_ckey`,`a_computerid`,`a_ip`,`who`,`adminwho`,`edits`,`unbanned`,`unbanned_datetime`,`unbanned_ckey`,`unbanned_computerid`,`unbanned_ip`) VALUES (null, Now(), '[serverip]', '[bantype_str]', '[reason]', '[job]', [(duration)?"[duration]":"0"], [(rounds)?"[rounds]":"0"], Now() + INTERVAL [(duration>0) ? duration : 0] MINUTE, '[ckey]', '[computerid]', '[ip]', '[a_ckey]', '[a_computerid]', '[a_ip]', '[who]', '[adminwho]', '', null, null, null, null, null)"
|
||||
var/DBQuery/query_insert = dbcon.NewQuery(sql)
|
||||
query_insert.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Ban saved to database.")]</span>")
|
||||
message_admins("[key_name_admin(usr)] has added a [bantype_str] for [ckey] [(job)?"([job])":""] [(duration > 0)?"([duration] minutes)":""] with the reason: \"[reason]\" to the ban database.",1)
|
||||
|
||||
|
||||
|
||||
/datum/admins/proc/DB_ban_unban(var/ckey, var/bantype, var/job = "")
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
var/bantype_str
|
||||
if(bantype)
|
||||
var/bantype_pass = 0
|
||||
switch(bantype)
|
||||
if(BANTYPE_PERMA)
|
||||
bantype_str = "PERMABAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_TEMP)
|
||||
bantype_str = "TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_PERMA)
|
||||
bantype_str = "JOB_PERMABAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_JOB_TEMP)
|
||||
bantype_str = "JOB_TEMPBAN"
|
||||
bantype_pass = 1
|
||||
if(BANTYPE_ANY_FULLBAN)
|
||||
bantype_str = "ANY"
|
||||
bantype_pass = 1
|
||||
if( !bantype_pass ) return
|
||||
|
||||
var/bantype_sql
|
||||
if(bantype_str == "ANY")
|
||||
bantype_sql = "(bantype = 'PERMABAN' OR (bantype = 'TEMPBAN' AND expiration_time > Now() ) )"
|
||||
else
|
||||
bantype_sql = "bantype = '[bantype_str]'"
|
||||
|
||||
var/sql = "SELECT id FROM erro_ban WHERE ckey = '[ckey]' AND [bantype_sql] AND (unbanned is null OR unbanned = false)"
|
||||
if(job)
|
||||
sql += " AND job = '[job]'"
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
return
|
||||
|
||||
var/ban_id
|
||||
var/ban_number = 0 //failsafe
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery(sql)
|
||||
query.Execute()
|
||||
while(query.NextRow())
|
||||
ban_id = query.item[1]
|
||||
ban_number++;
|
||||
|
||||
if(ban_number == 0)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to no bans fitting the search criteria. If this is not a legacy ban you should contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
if(ban_number > 1)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to multiple bans fitting the search criteria. Note down the ckey, job and current time and contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
if(istext(ban_id))
|
||||
ban_id = text2num(ban_id)
|
||||
if(!isnum(ban_id))
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to a ban ID mismatch. Contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
DB_ban_unban_by_id(ban_id)
|
||||
|
||||
/datum/admins/proc/DB_ban_edit(var/banid = null, var/param = null)
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
if(!isnum(banid) || !istext(param))
|
||||
to_chat(usr, "Cancelled")
|
||||
return
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT ckey, duration, reason FROM erro_ban WHERE id = [banid]")
|
||||
query.Execute()
|
||||
|
||||
var/eckey = usr.ckey //Editing admin ckey
|
||||
var/pckey //(banned) Player ckey
|
||||
var/duration //Old duration
|
||||
var/reason //Old reason
|
||||
|
||||
if(query.NextRow())
|
||||
pckey = query.item[1]
|
||||
duration = query.item[2]
|
||||
reason = query.item[3]
|
||||
else
|
||||
to_chat(usr, "<span class='filter_adminlog'>Invalid ban id. Contact the database admin</span>")
|
||||
return
|
||||
|
||||
reason = sql_sanitize_text(reason)
|
||||
var/value
|
||||
|
||||
switch(param)
|
||||
if("reason")
|
||||
if(!value)
|
||||
value = sanitize(tgui_input_text(usr, "Insert the new reason for [pckey]'s ban", "New Reason", "[reason]", null))
|
||||
value = sql_sanitize_text(value)
|
||||
if(!value)
|
||||
to_chat(usr, "Cancelled")
|
||||
return
|
||||
|
||||
var/DBQuery/update_query = dbcon.NewQuery("UPDATE erro_ban SET reason = '[value]', edits = CONCAT(edits,'- [eckey] changed ban reason from <cite><b>\\\"[reason]\\\"</b></cite> to <cite><b>\\\"[value]\\\"</b></cite><BR>') WHERE id = [banid]")
|
||||
update_query.Execute()
|
||||
message_admins("[key_name_admin(usr)] has edited a ban for [pckey]'s reason from [reason] to [value]",1)
|
||||
if("duration")
|
||||
if(!value)
|
||||
value = tgui_input_number(usr, "Insert the new duration (in minutes) for [pckey]'s ban", "New Duration", "[duration]", null)
|
||||
if(!isnum(value) || !value)
|
||||
to_chat(usr, "Cancelled")
|
||||
return
|
||||
|
||||
var/DBQuery/update_query = dbcon.NewQuery("UPDATE erro_ban SET duration = [value], edits = CONCAT(edits,'- [eckey] changed ban duration from [duration] to [value]<br>'), expiration_time = DATE_ADD(bantime, INTERVAL [value] MINUTE) WHERE id = [banid]")
|
||||
message_admins("[key_name_admin(usr)] has edited a ban for [pckey]'s duration from [duration] to [value]",1)
|
||||
update_query.Execute()
|
||||
if("unban")
|
||||
if(tgui_alert(usr, "Unban [pckey]?", "Unban?", list("Yes", "No")) == "Yes")
|
||||
DB_ban_unban_by_id(banid)
|
||||
return
|
||||
to_chat(usr, "<span class='filter_adminlog'>Cancelled</span>")
|
||||
return
|
||||
|
||||
/datum/admins/proc/DB_ban_unban_by_id(var/id)
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
var/sql = "SELECT ckey FROM erro_ban WHERE id = [id]"
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
return
|
||||
|
||||
var/ban_number = 0 //failsafe
|
||||
|
||||
var/pckey
|
||||
var/DBQuery/query = dbcon.NewQuery(sql)
|
||||
query.Execute()
|
||||
while(query.NextRow())
|
||||
pckey = query.item[1]
|
||||
ban_number++;
|
||||
|
||||
if(ban_number == 0)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to a ban id not being present in the database.")]</span>")
|
||||
return
|
||||
|
||||
if(ban_number > 1)
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Database update failed due to multiple bans having the same ID. Contact the database admin.")]</span>")
|
||||
return
|
||||
|
||||
if(!src.owner || !istype(src.owner, /client))
|
||||
return
|
||||
|
||||
var/unban_ckey = src.owner:ckey
|
||||
var/unban_computerid = src.owner:computer_id
|
||||
var/unban_ip = src.owner:address
|
||||
|
||||
var/sql_update = "UPDATE erro_ban SET unbanned = 1, unbanned_datetime = Now(), unbanned_ckey = '[unban_ckey]', unbanned_computerid = '[unban_computerid]', unbanned_ip = '[unban_ip]' WHERE id = [id]"
|
||||
message_admins("[key_name_admin(usr)] has lifted [pckey]'s ban.",1)
|
||||
|
||||
var/DBQuery/query_update = dbcon.NewQuery(sql_update)
|
||||
query_update.Execute()
|
||||
|
||||
|
||||
/client/proc/DB_ban_panel()
|
||||
set category = "Admin"
|
||||
set name = "Banning Panel"
|
||||
set desc = "Edit admin permissions"
|
||||
|
||||
if(!holder)
|
||||
return
|
||||
|
||||
holder.DB_ban_panel()
|
||||
|
||||
|
||||
/datum/admins/proc/DB_ban_panel(var/playerckey = null, var/adminckey = null, var/playerip = null, var/playercid = null, var/dbbantype = null, var/match = null)
|
||||
if(!usr.client)
|
||||
return
|
||||
|
||||
if(!check_rights(R_BAN)) return
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Failed to establish database connection")]</span>")
|
||||
return
|
||||
|
||||
var/output = "<div align='center'><table width='90%'><tr>"
|
||||
|
||||
output += "<td width='35%' align='center'>"
|
||||
output += "<h1>Banning panel</h1>"
|
||||
output += "</td>"
|
||||
|
||||
output += "<td width='65%' align='center' bgcolor='#f9f9f9'>"
|
||||
|
||||
output += "<form method='GET' action='?src=\ref[src]'>[HrefTokenFormField()]"
|
||||
output += "<b>Add custom ban:</b> (ONLY use this if you can't ban through any other method)"
|
||||
output += "<input type='hidden' name='src' value='\ref[src]'>"
|
||||
output += "<table width='100%'><tr>"
|
||||
output += "<td width='50%' align='right'><b>Ban type:</b><select name='dbbanaddtype'>"
|
||||
output += "<option value=''>--</option>"
|
||||
output += "<option value='[BANTYPE_PERMA]'>PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_TEMP]'>TEMPBAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_PERMA]'>JOB PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_TEMP]'>JOB TEMPBAN</option>"
|
||||
output += "</select></td>"
|
||||
output += "<td width='50%' align='right'><b>Ckey:</b> <input type='text' name='dbbanaddckey'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>IP:</b> <input type='text' name='dbbanaddip'></td>"
|
||||
output += "<td width='50%' align='right'><b>CID:</b> <input type='text' name='dbbanaddcid'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>Duration:</b> <input type='text' name='dbbaddduration'></td>"
|
||||
output += "<td width='50%' align='right'><b>Job:</b><select name='dbbanaddjob'>"
|
||||
output += "<option value=''>--</option>"
|
||||
for(var/j in get_all_jobs())
|
||||
output += "<option value='[j]'>[j]</option>"
|
||||
for(var/j in SSjob.get_job_titles_in_department(DEPARTMENT_SYNTHETIC))
|
||||
output += "<option value='[j]'>[j]</option>"
|
||||
var/list/bantypes = list("traitor","changeling","operative","revolutionary","cultist","wizard") //For legacy bans.
|
||||
for(var/antag_type in all_antag_types) // Grab other bans.
|
||||
var/datum/antagonist/antag = all_antag_types[antag_type]
|
||||
bantypes |= antag.bantype
|
||||
for(var/j in bantypes)
|
||||
output += "<option value='[j]'>[j]</option>"
|
||||
output += "</select></td></tr></table>"
|
||||
output += "<b>Reason:<br></b><textarea name='dbbanreason' cols='50'></textarea><br>"
|
||||
output += "<input type='submit' value='Add ban'>"
|
||||
output += "</form>"
|
||||
|
||||
output += "</td>"
|
||||
output += "</tr>"
|
||||
output += "</table>"
|
||||
|
||||
output += "<form method='GET' action='?src=\ref[src]'>[HrefTokenFormField()]"
|
||||
output += "<table width='60%'><tr><td colspan='2' align='left'><b>Search:</b>"
|
||||
output += "<input type='hidden' name='src' value='\ref[src]'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>Ckey:</b> <input type='text' name='dbsearchckey' value='[playerckey]'></td>"
|
||||
output += "<td width='50%' align='right'><b>Admin ckey:</b> <input type='text' name='dbsearchadmin' value='[adminckey]'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right'><b>IP:</b> <input type='text' name='dbsearchip' value='[playerip]'></td>"
|
||||
output += "<td width='50%' align='right'><b>CID:</b> <input type='text' name='dbsearchcid' value='[playercid]'></td></tr>"
|
||||
output += "<tr><td width='50%' align='right' colspan='2'><b>Ban type:</b><select name='dbsearchbantype'>"
|
||||
output += "<option value=''>--</option>"
|
||||
output += "<option value='[BANTYPE_PERMA]'>PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_TEMP]'>TEMPBAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_PERMA]'>JOB PERMABAN</option>"
|
||||
output += "<option value='[BANTYPE_JOB_TEMP]'>JOB TEMPBAN</option>"
|
||||
output += "</select></td></tr></table>"
|
||||
output += "<br><input type='submit' value='search'><br>"
|
||||
output += "<input type='checkbox' value='[match]' name='dbmatch' [match? "checked=\"1\"" : null]> Match(min. 3 characters to search by key or ip, and 7 to search by cid)<br>"
|
||||
output += "</form>"
|
||||
output += "Please note that all jobban bans or unbans are in-effect the following round.<br>"
|
||||
output += "This search shows only last 100 bans."
|
||||
|
||||
if(adminckey || playerckey || playerip || playercid || dbbantype)
|
||||
|
||||
adminckey = ckey(adminckey)
|
||||
playerckey = ckey(playerckey)
|
||||
playerip = sql_sanitize_text(playerip)
|
||||
playercid = sql_sanitize_text(playercid)
|
||||
|
||||
if(adminckey || playerckey || playerip || playercid || dbbantype)
|
||||
|
||||
var/blcolor = "#ffeeee" //banned light
|
||||
var/bdcolor = "#ffdddd" //banned dark
|
||||
var/ulcolor = "#eeffee" //unbanned light
|
||||
var/udcolor = "#ddffdd" //unbanned dark
|
||||
var/alcolor = "#eeeeff" // auto-unbanned light
|
||||
var/adcolor = "#ddddff" // auto-unbanned dark
|
||||
|
||||
output += "<table width='90%' bgcolor='#e3e3e3' cellpadding='5' cellspacing='0' align='center'>"
|
||||
output += "<tr>"
|
||||
output += "<th width='25%'><b>TYPE</b></th>"
|
||||
output += "<th width='20%'><b>CKEY</b></th>"
|
||||
output += "<th width='20%'><b>TIME APPLIED</b></th>"
|
||||
output += "<th width='20%'><b>ADMIN</b></th>"
|
||||
output += "<th width='15%'><b>OPTIONS</b></th>"
|
||||
output += "</tr>"
|
||||
|
||||
var/adminsearch = ""
|
||||
var/playersearch = ""
|
||||
var/ipsearch = ""
|
||||
var/cidsearch = ""
|
||||
var/bantypesearch = ""
|
||||
|
||||
if(!match)
|
||||
if(adminckey)
|
||||
adminsearch = "AND a_ckey = '[adminckey]' "
|
||||
if(playerckey)
|
||||
playersearch = "AND ckey = '[playerckey]' "
|
||||
if(playerip)
|
||||
ipsearch = "AND ip = '[playerip]' "
|
||||
if(playercid)
|
||||
cidsearch = "AND computerid = '[playercid]' "
|
||||
else
|
||||
if(adminckey && length(adminckey) >= 3)
|
||||
adminsearch = "AND a_ckey LIKE '[adminckey]%' "
|
||||
if(playerckey && length(playerckey) >= 3)
|
||||
playersearch = "AND ckey LIKE '[playerckey]%' "
|
||||
if(playerip && length(playerip) >= 3)
|
||||
ipsearch = "AND ip LIKE '[playerip]%' "
|
||||
if(playercid && length(playercid) >= 7)
|
||||
cidsearch = "AND computerid LIKE '[playercid]%' "
|
||||
|
||||
if(dbbantype)
|
||||
bantypesearch = "AND bantype = "
|
||||
|
||||
switch(dbbantype)
|
||||
if(BANTYPE_TEMP)
|
||||
bantypesearch += "'TEMPBAN' "
|
||||
if(BANTYPE_JOB_PERMA)
|
||||
bantypesearch += "'JOB_PERMABAN' "
|
||||
if(BANTYPE_JOB_TEMP)
|
||||
bantypesearch += "'JOB_TEMPBAN' "
|
||||
else
|
||||
bantypesearch += "'PERMABAN' "
|
||||
|
||||
var/DBQuery/select_query = dbcon.NewQuery("SELECT id, bantime, bantype, reason, job, duration, expiration_time, ckey, a_ckey, unbanned, unbanned_ckey, unbanned_datetime, edits, ip, computerid FROM erro_ban WHERE 1 [playersearch] [adminsearch] [ipsearch] [cidsearch] [bantypesearch] ORDER BY bantime DESC LIMIT 100")
|
||||
select_query.Execute()
|
||||
|
||||
var/now = time2text(world.realtime, "YYYY-MM-DD hh:mm:ss") // MUST BE the same format as SQL gives us the dates in, and MUST be least to most specific (i.e. year, month, day not day, month, year)
|
||||
|
||||
while(select_query.NextRow())
|
||||
var/banid = select_query.item[1]
|
||||
var/bantime = select_query.item[2]
|
||||
var/bantype = select_query.item[3]
|
||||
var/reason = select_query.item[4]
|
||||
var/job = select_query.item[5]
|
||||
var/duration = select_query.item[6]
|
||||
var/expiration = select_query.item[7]
|
||||
var/ckey = select_query.item[8]
|
||||
var/ackey = select_query.item[9]
|
||||
var/unbanned = select_query.item[10]
|
||||
var/unbanckey = select_query.item[11]
|
||||
var/unbantime = select_query.item[12]
|
||||
var/edits = select_query.item[13]
|
||||
var/ip = select_query.item[14]
|
||||
var/cid = select_query.item[15]
|
||||
|
||||
// true if this ban has expired
|
||||
var/auto = (bantype in list("TEMPBAN", "JOB_TEMPBAN")) && now > expiration // oh how I love ISO 8601 (ish) date strings
|
||||
|
||||
var/lcolor = blcolor
|
||||
var/dcolor = bdcolor
|
||||
if(unbanned)
|
||||
lcolor = ulcolor
|
||||
dcolor = udcolor
|
||||
else if(auto)
|
||||
lcolor = alcolor
|
||||
dcolor = adcolor
|
||||
|
||||
var/typedesc =""
|
||||
switch(bantype)
|
||||
if("PERMABAN")
|
||||
typedesc = "<font color='red'><b>PERMABAN</b></font>"
|
||||
if("TEMPBAN")
|
||||
typedesc = "<b>TEMPBAN</b><br><font size='2'>([duration] minutes) [(unbanned || auto) ? "" : "(<a href=\"byond://?src=\ref[src];[HrefToken()];dbbanedit=duration;dbbanid=[banid]\">Edit</a>)"]<br>Expires [expiration]</font>"
|
||||
if("JOB_PERMABAN")
|
||||
typedesc = "<b>JOBBAN</b><br><font size='2'>([job])</font>"
|
||||
if("JOB_TEMPBAN")
|
||||
typedesc = "<b>TEMP JOBBAN</b><br><font size='2'>([job])<br>([duration] minutes<br>Expires [expiration]</font>"
|
||||
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center'>[typedesc]</td>"
|
||||
output += "<td align='center'><b>[ckey]</b></td>"
|
||||
output += "<td align='center'>[bantime]</td>"
|
||||
output += "<td align='center'><b>[ackey]</b></td>"
|
||||
output += "<td align='center'>[(unbanned || auto) ? "" : "<b><a href=\"byond://?src=\ref[src];[HrefToken()];dbbanedit=unban;dbbanid=[banid]\">Unban</a></b>"]</td>"
|
||||
output += "</tr>"
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='2' bgcolor=''><b>IP:</b> [ip]</td>"
|
||||
output += "<td align='center' colspan='3' bgcolor=''><b>CIP:</b> [cid]</td>"
|
||||
output += "</tr>"
|
||||
output += "<tr bgcolor='[lcolor]'>"
|
||||
output += "<td align='center' colspan='5'><b>Reason: [(unbanned || auto) ? "" : "(<a href=\"byond://?src=\ref[src];[HrefToken()];dbbanedit=reason;dbbanid=[banid]\">Edit</a>)"]</b> <cite>\"[reason]\"</cite></td>"
|
||||
output += "</tr>"
|
||||
if(edits)
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='5'><b>EDITS</b></td>"
|
||||
output += "</tr>"
|
||||
output += "<tr bgcolor='[lcolor]'>"
|
||||
output += "<td align='center' colspan='5'><font size='2'>[edits]</font></td>"
|
||||
output += "</tr>"
|
||||
if(unbanned)
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='5' bgcolor=''><b>UNBANNED by admin [unbanckey] on [unbantime]</b></td>"
|
||||
output += "</tr>"
|
||||
else if(auto)
|
||||
output += "<tr bgcolor='[dcolor]'>"
|
||||
output += "<td align='center' colspan='5' bgcolor=''><b>EXPIRED at [expiration]</b></td>"
|
||||
output += "</tr>"
|
||||
output += "<tr>"
|
||||
output += "<td colspan='5' bgcolor='white'> </td>"
|
||||
output += "</tr>"
|
||||
|
||||
output += "</table></div>"
|
||||
|
||||
usr << browse(output,"window=lookupbans;size=900x700")
|
||||
|
||||
+229
-229
@@ -1,229 +1,229 @@
|
||||
var/CMinutes = null
|
||||
var/savefile/Banlist
|
||||
|
||||
|
||||
/proc/CheckBan(var/ckey, var/id, var/address)
|
||||
if(!Banlist) // if Banlist cannot be located for some reason
|
||||
LoadBans() // try to load the bans
|
||||
if(!Banlist) // uh oh, can't find bans!
|
||||
return 0 // ABORT ABORT ABORT
|
||||
|
||||
. = list()
|
||||
var/appeal
|
||||
if(config && config.banappeals)
|
||||
appeal = "\nFor more information on your ban, or to appeal, head to <a href='[config.banappeals]'>[config.banappeals]</a>"
|
||||
Banlist.cd = "/base"
|
||||
if( "[ckey][id]" in Banlist.dir )
|
||||
Banlist.cd = "[ckey][id]"
|
||||
if (Banlist["temp"])
|
||||
if (!GetExp(Banlist["minutes"]))
|
||||
ClearTempbans()
|
||||
return 0
|
||||
else
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: [GetExp(Banlist["minutes"])]\nBy: [Banlist["bannedby"]][appeal]"
|
||||
else
|
||||
Banlist.cd = "/base/[ckey][id]"
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: <B>PERMANENT</B>\nBy: [Banlist["bannedby"]][appeal]"
|
||||
.["reason"] = "ckey/id"
|
||||
return .
|
||||
else
|
||||
for (var/A in Banlist.dir)
|
||||
Banlist.cd = "/base/[A]"
|
||||
var/matches
|
||||
if( ckey == Banlist["key"] )
|
||||
matches += "ckey"
|
||||
if( id == Banlist["id"] )
|
||||
if(matches)
|
||||
matches += "/"
|
||||
matches += "id"
|
||||
if( address == Banlist["ip"] )
|
||||
if(matches)
|
||||
matches += "/"
|
||||
matches += "ip"
|
||||
|
||||
if(matches)
|
||||
if(Banlist["temp"])
|
||||
if (!GetExp(Banlist["minutes"]))
|
||||
ClearTempbans()
|
||||
return 0
|
||||
else
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: [GetExp(Banlist["minutes"])]\nBy: [Banlist["bannedby"]][appeal]"
|
||||
else
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: <B>PERMANENT</B>\nBy: [Banlist["bannedby"]][appeal]"
|
||||
.["reason"] = matches
|
||||
return .
|
||||
return 0
|
||||
|
||||
/proc/UpdateTime() //No idea why i made this a proc.
|
||||
CMinutes = (world.realtime / 10) / 60
|
||||
return 1
|
||||
|
||||
/hook/startup/proc/loadBans()
|
||||
return LoadBans()
|
||||
|
||||
/proc/LoadBans()
|
||||
|
||||
Banlist = new("data/banlist.bdb")
|
||||
log_admin("Loading Banlist")
|
||||
|
||||
if (!length(Banlist.dir)) log_admin("Banlist is empty.")
|
||||
|
||||
if (!Banlist.dir.Find("base"))
|
||||
log_admin("Banlist missing base dir.")
|
||||
Banlist.dir.Add("base")
|
||||
Banlist.cd = "/base"
|
||||
else if (Banlist.dir.Find("base"))
|
||||
Banlist.cd = "/base"
|
||||
|
||||
ClearTempbans()
|
||||
return 1
|
||||
|
||||
/proc/ClearTempbans()
|
||||
UpdateTime()
|
||||
|
||||
Banlist.cd = "/base"
|
||||
for (var/A in Banlist.dir)
|
||||
Banlist.cd = "/base/[A]"
|
||||
if (!Banlist["key"] || !Banlist["id"])
|
||||
RemoveBan(A)
|
||||
log_admin("Invalid Ban.")
|
||||
message_admins("Invalid Ban.")
|
||||
continue
|
||||
|
||||
if (!Banlist["temp"]) continue
|
||||
if (CMinutes >= Banlist["minutes"]) RemoveBan(A)
|
||||
|
||||
return 1
|
||||
|
||||
|
||||
/proc/AddBan(ckey, computerid, reason, bannedby, temp, minutes, address)
|
||||
|
||||
var/bantimestamp
|
||||
|
||||
if (temp)
|
||||
UpdateTime()
|
||||
bantimestamp = CMinutes + minutes
|
||||
|
||||
Banlist.cd = "/base"
|
||||
if ( Banlist.dir.Find("[ckey][computerid]") )
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Ban already exists.</span>")
|
||||
return 0
|
||||
else
|
||||
Banlist.dir.Add("[ckey][computerid]")
|
||||
Banlist.cd = "/base/[ckey][computerid]"
|
||||
Banlist["key"] << ckey
|
||||
Banlist["id"] << computerid
|
||||
Banlist["ip"] << address
|
||||
Banlist["reason"] << reason
|
||||
Banlist["bannedby"] << bannedby
|
||||
Banlist["temp"] << temp
|
||||
if (temp)
|
||||
Banlist["minutes"] << bantimestamp
|
||||
admin_action_message(bannedby, ckey, "banned", reason, temp ? minutes : -1) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/RemoveBan(foldername)
|
||||
var/key
|
||||
var/id
|
||||
|
||||
Banlist.cd = "/base/[foldername]"
|
||||
Banlist["key"] >> key
|
||||
Banlist["id"] >> id
|
||||
Banlist.cd = "/base"
|
||||
|
||||
if (!Banlist.dir.Remove(foldername)) return 0
|
||||
|
||||
if(!usr)
|
||||
log_admin("Ban Expired: [key]")
|
||||
message_admins("Ban Expired: [key]")
|
||||
else
|
||||
ban_unban_log_save("[key_name_admin(usr)] unbanned [key]")
|
||||
log_admin("[key_name_admin(usr)] unbanned [key]")
|
||||
message_admins("[key_name_admin(usr)] unbanned: [key]")
|
||||
feedback_inc("ban_unban",1)
|
||||
usr.client.holder.DB_ban_unban( ckey(key), BANTYPE_ANY_FULLBAN)
|
||||
for (var/A in Banlist.dir)
|
||||
Banlist.cd = "/base/[A]"
|
||||
if (key == Banlist["key"] /*|| id == Banlist["id"]*/)
|
||||
Banlist.cd = "/base"
|
||||
Banlist.dir.Remove(A)
|
||||
continue
|
||||
admin_action_message(usr.key, key, "unbanned", "\[Unban\]", 0) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/GetExp(minutes as num)
|
||||
UpdateTime()
|
||||
var/exp = minutes - CMinutes
|
||||
if (exp <= 0)
|
||||
return 0
|
||||
else
|
||||
var/timeleftstring
|
||||
if (exp >= 1440) //1440 = 1 day in minutes
|
||||
timeleftstring = "[round(exp / 1440, 0.1)] Days"
|
||||
else if (exp >= 60) //60 = 1 hour in minutes
|
||||
timeleftstring = "[round(exp / 60, 0.1)] Hours"
|
||||
else
|
||||
timeleftstring = "[exp] Minutes"
|
||||
return timeleftstring
|
||||
|
||||
/datum/admins/proc/unbanpanel()
|
||||
var/count = 0
|
||||
var/dat
|
||||
//var/dat = "<HR><B>Unban Player:</B> <font color='blue'>(U) = Unban</font> , (E) = Edit Ban <font color='green'>(Total<HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 ></font>"
|
||||
Banlist.cd = "/base"
|
||||
for (var/A in Banlist.dir)
|
||||
count++
|
||||
Banlist.cd = "/base/[A]"
|
||||
var/ref = "\ref[src]"
|
||||
var/key = Banlist["key"]
|
||||
var/id = Banlist["id"]
|
||||
var/ip = Banlist["ip"]
|
||||
var/reason = Banlist["reason"]
|
||||
var/by = Banlist["bannedby"]
|
||||
var/expiry
|
||||
if(Banlist["temp"])
|
||||
expiry = GetExp(Banlist["minutes"])
|
||||
if(!expiry) expiry = "Removal Pending"
|
||||
else expiry = "Permaban"
|
||||
|
||||
dat += text("<tr><td><A href='?src=[ref];[HrefToken()];unbanf=[key][id]'>(U)</A><A href='?src=[ref];[HrefToken()];unbane=[key][id]'>(E)</A> Key: <B>[key]</B></td><td>ComputerID: <B>[id]</B></td><td>IP: <B>[ip]</B></td><td> [expiry]</td><td>(By: [by])</td><td>(Reason: [reason])</td></tr>")
|
||||
|
||||
dat += "</table>"
|
||||
dat = "<HR><B>Bans:</B> <FONT COLOR=blue>(U) = Unban , (E) = Edit Ban</FONT> - <FONT COLOR=green>([count] Bans)</FONT><HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 >[dat]"
|
||||
usr << browse(dat, "window=unbanp;size=875x400")
|
||||
|
||||
//////////////////////////////////// DEBUG ////////////////////////////////////
|
||||
|
||||
/proc/CreateBans()
|
||||
|
||||
UpdateTime()
|
||||
|
||||
var/i
|
||||
var/last
|
||||
|
||||
for(i=0, i<1001, i++)
|
||||
var/a = pick(1,0)
|
||||
var/b = pick(1,0)
|
||||
if(b)
|
||||
Banlist.cd = "/base"
|
||||
Banlist.dir.Add("trash[i]trashid[i]")
|
||||
Banlist.cd = "/base/trash[i]trashid[i]"
|
||||
to_chat(Banlist["key"], "trash[i]")
|
||||
else
|
||||
Banlist.cd = "/base"
|
||||
Banlist.dir.Add("[last]trashid[i]")
|
||||
Banlist.cd = "/base/[last]trashid[i]"
|
||||
Banlist["key"] << last
|
||||
to_chat(Banlist["id"], "trashid[i]")
|
||||
to_chat(Banlist["reason"], "Trashban[i].")
|
||||
Banlist["temp"] << a
|
||||
Banlist["minutes"] << CMinutes + rand(1,2000)
|
||||
to_chat(Banlist["bannedby"], "trashmin")
|
||||
last = "trash[i]"
|
||||
|
||||
Banlist.cd = "/base"
|
||||
|
||||
/proc/ClearAllBans()
|
||||
Banlist.cd = "/base"
|
||||
for (var/A in Banlist.dir)
|
||||
RemoveBan(A)
|
||||
var/CMinutes = null
|
||||
var/savefile/Banlist
|
||||
|
||||
|
||||
/proc/CheckBan(var/ckey, var/id, var/address)
|
||||
if(!Banlist) // if Banlist cannot be located for some reason
|
||||
LoadBans() // try to load the bans
|
||||
if(!Banlist) // uh oh, can't find bans!
|
||||
return 0 // ABORT ABORT ABORT
|
||||
|
||||
. = list()
|
||||
var/appeal
|
||||
if(config && config.banappeals)
|
||||
appeal = "\nFor more information on your ban, or to appeal, head to <a href='[config.banappeals]'>[config.banappeals]</a>"
|
||||
Banlist.cd = "/base"
|
||||
if( "[ckey][id]" in Banlist.dir )
|
||||
Banlist.cd = "[ckey][id]"
|
||||
if (Banlist["temp"])
|
||||
if (!GetExp(Banlist["minutes"]))
|
||||
ClearTempbans()
|
||||
return 0
|
||||
else
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: [GetExp(Banlist["minutes"])]\nBy: [Banlist["bannedby"]][appeal]"
|
||||
else
|
||||
Banlist.cd = "/base/[ckey][id]"
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: <B>PERMANENT</B>\nBy: [Banlist["bannedby"]][appeal]"
|
||||
.["reason"] = "ckey/id"
|
||||
return .
|
||||
else
|
||||
for (var/A in Banlist.dir)
|
||||
Banlist.cd = "/base/[A]"
|
||||
var/matches
|
||||
if( ckey == Banlist["key"] )
|
||||
matches += "ckey"
|
||||
if( id == Banlist["id"] )
|
||||
if(matches)
|
||||
matches += "/"
|
||||
matches += "id"
|
||||
if( address == Banlist["ip"] )
|
||||
if(matches)
|
||||
matches += "/"
|
||||
matches += "ip"
|
||||
|
||||
if(matches)
|
||||
if(Banlist["temp"])
|
||||
if (!GetExp(Banlist["minutes"]))
|
||||
ClearTempbans()
|
||||
return 0
|
||||
else
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: [GetExp(Banlist["minutes"])]\nBy: [Banlist["bannedby"]][appeal]"
|
||||
else
|
||||
.["desc"] = "\nReason: [Banlist["reason"]]\nExpires: <B>PERMANENT</B>\nBy: [Banlist["bannedby"]][appeal]"
|
||||
.["reason"] = matches
|
||||
return .
|
||||
return 0
|
||||
|
||||
/proc/UpdateTime() //No idea why i made this a proc.
|
||||
CMinutes = (world.realtime / 10) / 60
|
||||
return 1
|
||||
|
||||
/hook/startup/proc/loadBans()
|
||||
return LoadBans()
|
||||
|
||||
/proc/LoadBans()
|
||||
|
||||
Banlist = new("data/banlist.bdb")
|
||||
log_admin("Loading Banlist")
|
||||
|
||||
if (!length(Banlist.dir)) log_admin("Banlist is empty.")
|
||||
|
||||
if (!Banlist.dir.Find("base"))
|
||||
log_admin("Banlist missing base dir.")
|
||||
Banlist.dir.Add("base")
|
||||
Banlist.cd = "/base"
|
||||
else if (Banlist.dir.Find("base"))
|
||||
Banlist.cd = "/base"
|
||||
|
||||
ClearTempbans()
|
||||
return 1
|
||||
|
||||
/proc/ClearTempbans()
|
||||
UpdateTime()
|
||||
|
||||
Banlist.cd = "/base"
|
||||
for (var/A in Banlist.dir)
|
||||
Banlist.cd = "/base/[A]"
|
||||
if (!Banlist["key"] || !Banlist["id"])
|
||||
RemoveBan(A)
|
||||
log_admin("Invalid Ban.")
|
||||
message_admins("Invalid Ban.")
|
||||
continue
|
||||
|
||||
if (!Banlist["temp"]) continue
|
||||
if (CMinutes >= Banlist["minutes"]) RemoveBan(A)
|
||||
|
||||
return 1
|
||||
|
||||
|
||||
/proc/AddBan(ckey, computerid, reason, bannedby, temp, minutes, address)
|
||||
|
||||
var/bantimestamp
|
||||
|
||||
if (temp)
|
||||
UpdateTime()
|
||||
bantimestamp = CMinutes + minutes
|
||||
|
||||
Banlist.cd = "/base"
|
||||
if ( Banlist.dir.Find("[ckey][computerid]") )
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Ban already exists.</span>")
|
||||
return 0
|
||||
else
|
||||
Banlist.dir.Add("[ckey][computerid]")
|
||||
Banlist.cd = "/base/[ckey][computerid]"
|
||||
Banlist["key"] << ckey
|
||||
Banlist["id"] << computerid
|
||||
Banlist["ip"] << address
|
||||
Banlist["reason"] << reason
|
||||
Banlist["bannedby"] << bannedby
|
||||
Banlist["temp"] << temp
|
||||
if (temp)
|
||||
Banlist["minutes"] << bantimestamp
|
||||
admin_action_message(bannedby, ckey, "banned", reason, temp ? minutes : -1) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/RemoveBan(foldername)
|
||||
var/key
|
||||
var/id
|
||||
|
||||
Banlist.cd = "/base/[foldername]"
|
||||
Banlist["key"] >> key
|
||||
Banlist["id"] >> id
|
||||
Banlist.cd = "/base"
|
||||
|
||||
if (!Banlist.dir.Remove(foldername)) return 0
|
||||
|
||||
if(!usr)
|
||||
log_admin("Ban Expired: [key]")
|
||||
message_admins("Ban Expired: [key]")
|
||||
else
|
||||
ban_unban_log_save("[key_name_admin(usr)] unbanned [key]")
|
||||
log_admin("[key_name_admin(usr)] unbanned [key]")
|
||||
message_admins("[key_name_admin(usr)] unbanned: [key]")
|
||||
feedback_inc("ban_unban",1)
|
||||
usr.client.holder.DB_ban_unban( ckey(key), BANTYPE_ANY_FULLBAN)
|
||||
for (var/A in Banlist.dir)
|
||||
Banlist.cd = "/base/[A]"
|
||||
if (key == Banlist["key"] /*|| id == Banlist["id"]*/)
|
||||
Banlist.cd = "/base"
|
||||
Banlist.dir.Remove(A)
|
||||
continue
|
||||
admin_action_message(usr.key, key, "unbanned", "\[Unban\]", 0) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/GetExp(minutes as num)
|
||||
UpdateTime()
|
||||
var/exp = minutes - CMinutes
|
||||
if (exp <= 0)
|
||||
return 0
|
||||
else
|
||||
var/timeleftstring
|
||||
if (exp >= 1440) //1440 = 1 day in minutes
|
||||
timeleftstring = "[round(exp / 1440, 0.1)] Days"
|
||||
else if (exp >= 60) //60 = 1 hour in minutes
|
||||
timeleftstring = "[round(exp / 60, 0.1)] Hours"
|
||||
else
|
||||
timeleftstring = "[exp] Minutes"
|
||||
return timeleftstring
|
||||
|
||||
/datum/admins/proc/unbanpanel()
|
||||
var/count = 0
|
||||
var/dat
|
||||
//var/dat = "<HR><B>Unban Player:</B> <font color='blue'>(U) = Unban</font> , (E) = Edit Ban <font color='green'>(Total<HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 ></font>"
|
||||
Banlist.cd = "/base"
|
||||
for (var/A in Banlist.dir)
|
||||
count++
|
||||
Banlist.cd = "/base/[A]"
|
||||
var/ref = "\ref[src]"
|
||||
var/key = Banlist["key"]
|
||||
var/id = Banlist["id"]
|
||||
var/ip = Banlist["ip"]
|
||||
var/reason = Banlist["reason"]
|
||||
var/by = Banlist["bannedby"]
|
||||
var/expiry
|
||||
if(Banlist["temp"])
|
||||
expiry = GetExp(Banlist["minutes"])
|
||||
if(!expiry) expiry = "Removal Pending"
|
||||
else expiry = "Permaban"
|
||||
|
||||
dat += text("<tr><td><A href='?src=[ref];[HrefToken()];unbanf=[key][id]'>(U)</A><A href='?src=[ref];[HrefToken()];unbane=[key][id]'>(E)</A> Key: <B>[key]</B></td><td>ComputerID: <B>[id]</B></td><td>IP: <B>[ip]</B></td><td> [expiry]</td><td>(By: [by])</td><td>(Reason: [reason])</td></tr>")
|
||||
|
||||
dat += "</table>"
|
||||
dat = "<HR><B>Bans:</B> <FONT COLOR=blue>(U) = Unban , (E) = Edit Ban</FONT> - <FONT COLOR=green>([count] Bans)</FONT><HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 >[dat]"
|
||||
usr << browse(dat, "window=unbanp;size=875x400")
|
||||
|
||||
//////////////////////////////////// DEBUG ////////////////////////////////////
|
||||
|
||||
/proc/CreateBans()
|
||||
|
||||
UpdateTime()
|
||||
|
||||
var/i
|
||||
var/last
|
||||
|
||||
for(i=0, i<1001, i++)
|
||||
var/a = pick(1,0)
|
||||
var/b = pick(1,0)
|
||||
if(b)
|
||||
Banlist.cd = "/base"
|
||||
Banlist.dir.Add("trash[i]trashid[i]")
|
||||
Banlist.cd = "/base/trash[i]trashid[i]"
|
||||
to_chat(Banlist["key"], "trash[i]")
|
||||
else
|
||||
Banlist.cd = "/base"
|
||||
Banlist.dir.Add("[last]trashid[i]")
|
||||
Banlist.cd = "/base/[last]trashid[i]"
|
||||
Banlist["key"] << last
|
||||
to_chat(Banlist["id"], "trashid[i]")
|
||||
to_chat(Banlist["reason"], "Trashban[i].")
|
||||
Banlist["temp"] << a
|
||||
Banlist["minutes"] << CMinutes + rand(1,2000)
|
||||
to_chat(Banlist["bannedby"], "trashmin")
|
||||
last = "trash[i]"
|
||||
|
||||
Banlist.cd = "/base"
|
||||
|
||||
/proc/ClearAllBans()
|
||||
Banlist.cd = "/base"
|
||||
for (var/A in Banlist.dir)
|
||||
RemoveBan(A)
|
||||
|
||||
@@ -1,89 +1,89 @@
|
||||
//By Carnwennan
|
||||
//fetches an external list and processes it into a list of ip addresses.
|
||||
//It then stores the processed list into a savefile for later use
|
||||
#define TORFILE "data/ToR_ban.bdb"
|
||||
#define TOR_UPDATE_INTERVAL 216000 //~6 hours
|
||||
|
||||
/proc/ToRban_isbanned(var/ip_address)
|
||||
var/savefile/F = new(TORFILE)
|
||||
if(F)
|
||||
if( ip_address in F.dir )
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/proc/ToRban_autoupdate()
|
||||
var/savefile/F = new(TORFILE)
|
||||
if(F)
|
||||
var/last_update
|
||||
F["last_update"] >> last_update
|
||||
if((last_update + TOR_UPDATE_INTERVAL) < world.realtime) //we haven't updated for a while
|
||||
ToRban_update()
|
||||
return
|
||||
|
||||
/proc/ToRban_update()
|
||||
spawn(0)
|
||||
log_misc("Downloading updated ToR data...")
|
||||
var/http[] = world.Export("https://check.torproject.org/exit-addresses")
|
||||
|
||||
var/list/rawlist = file2list(http["CONTENT"])
|
||||
if(rawlist.len)
|
||||
fdel(TORFILE)
|
||||
var/savefile/F = new(TORFILE)
|
||||
for( var/line in rawlist )
|
||||
if(!line) continue
|
||||
if( copytext(line,1,12) == "ExitAddress" )
|
||||
var/cleaned = copytext(line,13,length(line)-19)
|
||||
if(!cleaned) continue
|
||||
F[cleaned] << 1
|
||||
F["last_update"] << world.realtime
|
||||
log_misc("ToR data updated!")
|
||||
if(usr)
|
||||
to_chat(usr, "<span class='filter_adminlog'>ToRban updated.</span>")
|
||||
return
|
||||
log_misc("ToR data update aborted: no data.")
|
||||
return
|
||||
|
||||
/client/proc/ToRban(task in list("update","toggle","show","remove","remove all","find"))
|
||||
set name = "ToRban"
|
||||
set category = "Server"
|
||||
if(!holder) return
|
||||
switch(task)
|
||||
if("update")
|
||||
ToRban_update()
|
||||
if("toggle")
|
||||
if(config)
|
||||
if(config.ToRban)
|
||||
config.ToRban = 0
|
||||
message_admins(span_red("ToR banning disabled."))
|
||||
else
|
||||
config.ToRban = 1
|
||||
message_admins(span_green("ToR banning enabled."))
|
||||
if("show")
|
||||
var/savefile/F = new(TORFILE)
|
||||
var/dat
|
||||
if( length(F.dir) )
|
||||
for( var/i=1, i<=length(F.dir), i++ )
|
||||
dat += "<tr><td>#[i]</td><td> [F.dir[i]]</td></tr>"
|
||||
dat = "<table width='100%'>[dat]</table>"
|
||||
else
|
||||
dat = "No addresses in list."
|
||||
src << browse(dat,"window=ToRban_show")
|
||||
if("remove")
|
||||
var/savefile/F = new(TORFILE)
|
||||
var/choice = tgui_input_list(src,"Please select an IP address to remove from the ToR banlist:","Remove ToR ban", F.dir)
|
||||
if(choice)
|
||||
F.dir.Remove(choice)
|
||||
to_chat(src, "<span class='filter_adminlog'><b>Address removed</b></span>")
|
||||
if("remove all")
|
||||
to_chat(src, "<span class='filter_adminlog'><b>[TORFILE] was [fdel(TORFILE)?"":"not "]removed.</b></span>")
|
||||
if("find")
|
||||
var/input = tgui_input_text(src,"Please input an IP address to search for:","Find ToR ban",null)
|
||||
if(input)
|
||||
if(ToRban_isbanned(input))
|
||||
to_chat(src, "<span class='filter_adminlog'>[span_orange("<b>Address is a known ToR address</b>")]</span>")
|
||||
else
|
||||
to_chat(src, "<span class='filter_adminlog danger'>Address is not a known ToR address</span>")
|
||||
return
|
||||
|
||||
#undef TORFILE
|
||||
#undef TOR_UPDATE_INTERVAL
|
||||
//By Carnwennan
|
||||
//fetches an external list and processes it into a list of ip addresses.
|
||||
//It then stores the processed list into a savefile for later use
|
||||
#define TORFILE "data/ToR_ban.bdb"
|
||||
#define TOR_UPDATE_INTERVAL 216000 //~6 hours
|
||||
|
||||
/proc/ToRban_isbanned(var/ip_address)
|
||||
var/savefile/F = new(TORFILE)
|
||||
if(F)
|
||||
if( ip_address in F.dir )
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/proc/ToRban_autoupdate()
|
||||
var/savefile/F = new(TORFILE)
|
||||
if(F)
|
||||
var/last_update
|
||||
F["last_update"] >> last_update
|
||||
if((last_update + TOR_UPDATE_INTERVAL) < world.realtime) //we haven't updated for a while
|
||||
ToRban_update()
|
||||
return
|
||||
|
||||
/proc/ToRban_update()
|
||||
spawn(0)
|
||||
log_misc("Downloading updated ToR data...")
|
||||
var/http[] = world.Export("https://check.torproject.org/exit-addresses")
|
||||
|
||||
var/list/rawlist = file2list(http["CONTENT"])
|
||||
if(rawlist.len)
|
||||
fdel(TORFILE)
|
||||
var/savefile/F = new(TORFILE)
|
||||
for( var/line in rawlist )
|
||||
if(!line) continue
|
||||
if( copytext(line,1,12) == "ExitAddress" )
|
||||
var/cleaned = copytext(line,13,length(line)-19)
|
||||
if(!cleaned) continue
|
||||
F[cleaned] << 1
|
||||
F["last_update"] << world.realtime
|
||||
log_misc("ToR data updated!")
|
||||
if(usr)
|
||||
to_chat(usr, "<span class='filter_adminlog'>ToRban updated.</span>")
|
||||
return
|
||||
log_misc("ToR data update aborted: no data.")
|
||||
return
|
||||
|
||||
/client/proc/ToRban(task in list("update","toggle","show","remove","remove all","find"))
|
||||
set name = "ToRban"
|
||||
set category = "Server"
|
||||
if(!holder) return
|
||||
switch(task)
|
||||
if("update")
|
||||
ToRban_update()
|
||||
if("toggle")
|
||||
if(config)
|
||||
if(config.ToRban)
|
||||
config.ToRban = 0
|
||||
message_admins(span_red("ToR banning disabled."))
|
||||
else
|
||||
config.ToRban = 1
|
||||
message_admins(span_green("ToR banning enabled."))
|
||||
if("show")
|
||||
var/savefile/F = new(TORFILE)
|
||||
var/dat
|
||||
if( length(F.dir) )
|
||||
for( var/i=1, i<=length(F.dir), i++ )
|
||||
dat += "<tr><td>#[i]</td><td> [F.dir[i]]</td></tr>"
|
||||
dat = "<table width='100%'>[dat]</table>"
|
||||
else
|
||||
dat = "No addresses in list."
|
||||
src << browse(dat,"window=ToRban_show")
|
||||
if("remove")
|
||||
var/savefile/F = new(TORFILE)
|
||||
var/choice = tgui_input_list(src,"Please select an IP address to remove from the ToR banlist:","Remove ToR ban", F.dir)
|
||||
if(choice)
|
||||
F.dir.Remove(choice)
|
||||
to_chat(src, "<span class='filter_adminlog'><b>Address removed</b></span>")
|
||||
if("remove all")
|
||||
to_chat(src, "<span class='filter_adminlog'><b>[TORFILE] was [fdel(TORFILE)?"":"not "]removed.</b></span>")
|
||||
if("find")
|
||||
var/input = tgui_input_text(src,"Please input an IP address to search for:","Find ToR ban",null)
|
||||
if(input)
|
||||
if(ToRban_isbanned(input))
|
||||
to_chat(src, "<span class='filter_adminlog'>[span_orange("<b>Address is a known ToR address</b>")]</span>")
|
||||
else
|
||||
to_chat(src, "<span class='filter_adminlog danger'>Address is not a known ToR address</span>")
|
||||
return
|
||||
|
||||
#undef TORFILE
|
||||
#undef TOR_UPDATE_INTERVAL
|
||||
|
||||
+174
-174
@@ -1,174 +1,174 @@
|
||||
var/list/admin_ranks = list() //list of all ranks with associated rights
|
||||
|
||||
//load our rank - > rights associations
|
||||
/proc/load_admin_ranks()
|
||||
admin_ranks.Cut()
|
||||
|
||||
var/previous_rights = 0
|
||||
|
||||
//Clear profile access
|
||||
for(var/A in world.GetConfig("admin"))
|
||||
world.SetConfig("APP/admin", A, null)
|
||||
|
||||
//load text from file
|
||||
var/list/Lines = file2list("config/admin_ranks.txt")
|
||||
|
||||
//process each line seperately
|
||||
for(var/line in Lines)
|
||||
if(!length(line)) continue
|
||||
if(copytext(line,1,2) == "#") continue
|
||||
|
||||
var/list/List = splittext(line,"+")
|
||||
if(!List.len) continue
|
||||
|
||||
var/rank = ckeyEx(List[1])
|
||||
switch(rank)
|
||||
if(null,"") continue
|
||||
if("Removed") continue //Reserved
|
||||
|
||||
var/rights = 0
|
||||
for(var/i=2, i<=List.len, i++)
|
||||
switch(ckey(List[i]))
|
||||
if("@","prev") rights |= previous_rights
|
||||
if("buildmode","build") rights |= R_BUILDMODE
|
||||
if("admin") rights |= R_ADMIN
|
||||
if("ban") rights |= R_BAN
|
||||
if("fun") rights |= R_FUN
|
||||
if("server") rights |= R_SERVER
|
||||
if("debug") rights |= R_DEBUG
|
||||
if("permissions","rights") rights |= R_PERMISSIONS
|
||||
if("possess") rights |= R_POSSESS
|
||||
if("stealth") rights |= R_STEALTH
|
||||
if("rejuv","rejuvinate") rights |= R_REJUVINATE
|
||||
if("varedit") rights |= R_VAREDIT
|
||||
if("everything","host","all") rights |= (R_HOST | R_BUILDMODE | R_ADMIN | R_BAN | R_FUN | R_SERVER | R_DEBUG | R_PERMISSIONS | R_POSSESS | R_STEALTH | R_REJUVINATE | R_VAREDIT | R_SOUNDS | R_SPAWN | R_MOD| R_EVENT)
|
||||
if("sound","sounds") rights |= R_SOUNDS
|
||||
if("spawn","create") rights |= R_SPAWN
|
||||
if("mod") rights |= R_MOD
|
||||
if("event") rights |= R_EVENT
|
||||
|
||||
admin_ranks[rank] = rights
|
||||
previous_rights = rights
|
||||
|
||||
#ifdef TESTING
|
||||
var/msg = "Permission Sets Built:\n"
|
||||
for(var/rank in admin_ranks)
|
||||
msg += "\t[rank] - [admin_ranks[rank]]\n"
|
||||
testing(msg)
|
||||
#endif
|
||||
|
||||
/hook/startup/proc/loadAdmins()
|
||||
load_admins()
|
||||
return 1
|
||||
|
||||
/proc/load_admins()
|
||||
//clear the datums references
|
||||
admin_datums.Cut()
|
||||
for(var/client/C in GLOB.admins)
|
||||
C.remove_admin_verbs()
|
||||
C.holder = null
|
||||
GLOB.admins.Cut()
|
||||
|
||||
if(config.admin_legacy_system)
|
||||
load_admin_ranks()
|
||||
//Clear profile access
|
||||
for(var/A in world.GetConfig("admin"))
|
||||
world.SetConfig("APP/admin", A, null)
|
||||
|
||||
//load text from file
|
||||
var/list/Lines = file2list("config/admins.txt")
|
||||
|
||||
//process each line seperately
|
||||
for(var/line in Lines)
|
||||
if(!length(line)) continue
|
||||
if(copytext(line,1,2) == "#") continue
|
||||
|
||||
//Split the line at every "-"
|
||||
var/list/List = splittext(line, "-")
|
||||
if(!List.len) continue
|
||||
|
||||
//ckey is before the first "-"
|
||||
var/ckey = ckey(List[1])
|
||||
if(!ckey) continue
|
||||
|
||||
//rank follows the first "-"
|
||||
var/rank = ""
|
||||
if(List.len >= 2)
|
||||
rank = ckeyEx(List[2])
|
||||
|
||||
//load permissions associated with this rank
|
||||
var/rights = admin_ranks[rank]
|
||||
|
||||
//create the admin datum and store it for later use
|
||||
var/datum/admins/D = new /datum/admins(rank, rights, ckey)
|
||||
|
||||
if(D.rights & R_DEBUG) //grant profile access
|
||||
world.SetConfig("APP/admin", ckey, "role=admin")
|
||||
|
||||
//find the client for a ckey if they are connected and associate them with the new admin datum
|
||||
D.associate(GLOB.directory[ckey])
|
||||
|
||||
else
|
||||
//The current admin system uses SQL
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
error("Failed to connect to database in load_admins(). Reverting to legacy system.")
|
||||
log_misc("Failed to connect to database in load_admins(). Reverting to legacy system.")
|
||||
config.admin_legacy_system = 1
|
||||
load_admins()
|
||||
return
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT ckey, rank, level, flags FROM erro_admin")
|
||||
query.Execute()
|
||||
while(query.NextRow())
|
||||
var/ckey = query.item[1]
|
||||
var/rank = query.item[2]
|
||||
if(rank == "Removed") continue //This person was de-adminned. They are only in the admin list for archive purposes.
|
||||
|
||||
var/rights = query.item[4]
|
||||
if(istext(rights)) rights = text2num(rights)
|
||||
var/datum/admins/D = new /datum/admins(rank, rights, ckey)
|
||||
|
||||
if(D.rights & R_DEBUG) //grant profile access
|
||||
world.SetConfig("APP/admin", ckey, "role=admin")
|
||||
|
||||
//find the client for a ckey if they are connected and associate them with the new admin datum
|
||||
D.associate(GLOB.directory[ckey])
|
||||
if(!admin_datums)
|
||||
error("The database query in load_admins() resulted in no admins being added to the list. Reverting to legacy system.")
|
||||
log_misc("The database query in load_admins() resulted in no admins being added to the list. Reverting to legacy system.")
|
||||
config.admin_legacy_system = 1
|
||||
load_admins()
|
||||
return
|
||||
|
||||
#ifdef TESTING
|
||||
var/msg = "Admins Built:\n"
|
||||
for(var/ckey in admin_datums)
|
||||
var/rank
|
||||
var/datum/admins/D = admin_datums[ckey]
|
||||
if(D) rank = D.rank
|
||||
msg += "\t[ckey] - [rank]\n"
|
||||
testing(msg)
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef TESTING
|
||||
/client/verb/changerank(newrank in admin_ranks)
|
||||
if(holder)
|
||||
holder.rank = newrank
|
||||
holder.rights = admin_ranks[newrank]
|
||||
else
|
||||
holder = new /datum/admins(newrank,admin_ranks[newrank],ckey)
|
||||
remove_admin_verbs()
|
||||
holder.associate(src)
|
||||
|
||||
/client/verb/changerights(newrights as num)
|
||||
if(holder)
|
||||
holder.rights = newrights
|
||||
else
|
||||
holder = new /datum/admins("testing",newrights,ckey)
|
||||
remove_admin_verbs()
|
||||
holder.associate(src)
|
||||
|
||||
#endif
|
||||
var/list/admin_ranks = list() //list of all ranks with associated rights
|
||||
|
||||
//load our rank - > rights associations
|
||||
/proc/load_admin_ranks()
|
||||
admin_ranks.Cut()
|
||||
|
||||
var/previous_rights = 0
|
||||
|
||||
//Clear profile access
|
||||
for(var/A in world.GetConfig("admin"))
|
||||
world.SetConfig("APP/admin", A, null)
|
||||
|
||||
//load text from file
|
||||
var/list/Lines = file2list("config/admin_ranks.txt")
|
||||
|
||||
//process each line seperately
|
||||
for(var/line in Lines)
|
||||
if(!length(line)) continue
|
||||
if(copytext(line,1,2) == "#") continue
|
||||
|
||||
var/list/List = splittext(line,"+")
|
||||
if(!List.len) continue
|
||||
|
||||
var/rank = ckeyEx(List[1])
|
||||
switch(rank)
|
||||
if(null,"") continue
|
||||
if("Removed") continue //Reserved
|
||||
|
||||
var/rights = 0
|
||||
for(var/i=2, i<=List.len, i++)
|
||||
switch(ckey(List[i]))
|
||||
if("@","prev") rights |= previous_rights
|
||||
if("buildmode","build") rights |= R_BUILDMODE
|
||||
if("admin") rights |= R_ADMIN
|
||||
if("ban") rights |= R_BAN
|
||||
if("fun") rights |= R_FUN
|
||||
if("server") rights |= R_SERVER
|
||||
if("debug") rights |= R_DEBUG
|
||||
if("permissions","rights") rights |= R_PERMISSIONS
|
||||
if("possess") rights |= R_POSSESS
|
||||
if("stealth") rights |= R_STEALTH
|
||||
if("rejuv","rejuvinate") rights |= R_REJUVINATE
|
||||
if("varedit") rights |= R_VAREDIT
|
||||
if("everything","host","all") rights |= (R_HOST | R_BUILDMODE | R_ADMIN | R_BAN | R_FUN | R_SERVER | R_DEBUG | R_PERMISSIONS | R_POSSESS | R_STEALTH | R_REJUVINATE | R_VAREDIT | R_SOUNDS | R_SPAWN | R_MOD| R_EVENT)
|
||||
if("sound","sounds") rights |= R_SOUNDS
|
||||
if("spawn","create") rights |= R_SPAWN
|
||||
if("mod") rights |= R_MOD
|
||||
if("event") rights |= R_EVENT
|
||||
|
||||
admin_ranks[rank] = rights
|
||||
previous_rights = rights
|
||||
|
||||
#ifdef TESTING
|
||||
var/msg = "Permission Sets Built:\n"
|
||||
for(var/rank in admin_ranks)
|
||||
msg += "\t[rank] - [admin_ranks[rank]]\n"
|
||||
testing(msg)
|
||||
#endif
|
||||
|
||||
/hook/startup/proc/loadAdmins()
|
||||
load_admins()
|
||||
return 1
|
||||
|
||||
/proc/load_admins()
|
||||
//clear the datums references
|
||||
admin_datums.Cut()
|
||||
for(var/client/C in GLOB.admins)
|
||||
C.remove_admin_verbs()
|
||||
C.holder = null
|
||||
GLOB.admins.Cut()
|
||||
|
||||
if(config.admin_legacy_system)
|
||||
load_admin_ranks()
|
||||
//Clear profile access
|
||||
for(var/A in world.GetConfig("admin"))
|
||||
world.SetConfig("APP/admin", A, null)
|
||||
|
||||
//load text from file
|
||||
var/list/Lines = file2list("config/admins.txt")
|
||||
|
||||
//process each line seperately
|
||||
for(var/line in Lines)
|
||||
if(!length(line)) continue
|
||||
if(copytext(line,1,2) == "#") continue
|
||||
|
||||
//Split the line at every "-"
|
||||
var/list/List = splittext(line, "-")
|
||||
if(!List.len) continue
|
||||
|
||||
//ckey is before the first "-"
|
||||
var/ckey = ckey(List[1])
|
||||
if(!ckey) continue
|
||||
|
||||
//rank follows the first "-"
|
||||
var/rank = ""
|
||||
if(List.len >= 2)
|
||||
rank = ckeyEx(List[2])
|
||||
|
||||
//load permissions associated with this rank
|
||||
var/rights = admin_ranks[rank]
|
||||
|
||||
//create the admin datum and store it for later use
|
||||
var/datum/admins/D = new /datum/admins(rank, rights, ckey)
|
||||
|
||||
if(D.rights & R_DEBUG) //grant profile access
|
||||
world.SetConfig("APP/admin", ckey, "role=admin")
|
||||
|
||||
//find the client for a ckey if they are connected and associate them with the new admin datum
|
||||
D.associate(GLOB.directory[ckey])
|
||||
|
||||
else
|
||||
//The current admin system uses SQL
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
error("Failed to connect to database in load_admins(). Reverting to legacy system.")
|
||||
log_misc("Failed to connect to database in load_admins(). Reverting to legacy system.")
|
||||
config.admin_legacy_system = 1
|
||||
load_admins()
|
||||
return
|
||||
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT ckey, rank, level, flags FROM erro_admin")
|
||||
query.Execute()
|
||||
while(query.NextRow())
|
||||
var/ckey = query.item[1]
|
||||
var/rank = query.item[2]
|
||||
if(rank == "Removed") continue //This person was de-adminned. They are only in the admin list for archive purposes.
|
||||
|
||||
var/rights = query.item[4]
|
||||
if(istext(rights)) rights = text2num(rights)
|
||||
var/datum/admins/D = new /datum/admins(rank, rights, ckey)
|
||||
|
||||
if(D.rights & R_DEBUG) //grant profile access
|
||||
world.SetConfig("APP/admin", ckey, "role=admin")
|
||||
|
||||
//find the client for a ckey if they are connected and associate them with the new admin datum
|
||||
D.associate(GLOB.directory[ckey])
|
||||
if(!admin_datums)
|
||||
error("The database query in load_admins() resulted in no admins being added to the list. Reverting to legacy system.")
|
||||
log_misc("The database query in load_admins() resulted in no admins being added to the list. Reverting to legacy system.")
|
||||
config.admin_legacy_system = 1
|
||||
load_admins()
|
||||
return
|
||||
|
||||
#ifdef TESTING
|
||||
var/msg = "Admins Built:\n"
|
||||
for(var/ckey in admin_datums)
|
||||
var/rank
|
||||
var/datum/admins/D = admin_datums[ckey]
|
||||
if(D) rank = D.rank
|
||||
msg += "\t[ckey] - [rank]\n"
|
||||
testing(msg)
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef TESTING
|
||||
/client/verb/changerank(newrank in admin_ranks)
|
||||
if(holder)
|
||||
holder.rank = newrank
|
||||
holder.rights = admin_ranks[newrank]
|
||||
else
|
||||
holder = new /datum/admins(newrank,admin_ranks[newrank],ckey)
|
||||
remove_admin_verbs()
|
||||
holder.associate(src)
|
||||
|
||||
/client/verb/changerights(newrights as num)
|
||||
if(holder)
|
||||
holder.rights = newrights
|
||||
else
|
||||
holder = new /datum/admins("testing",newrights,ckey)
|
||||
remove_admin_verbs()
|
||||
holder.associate(src)
|
||||
|
||||
#endif
|
||||
|
||||
+182
-182
@@ -1,182 +1,182 @@
|
||||
// Reports are a way to notify admins of wrongdoings that happened
|
||||
// while no admin was present. They work a bit similar to news, but
|
||||
// they can only be read by admins and moderators.
|
||||
|
||||
// a single admin report
|
||||
/datum//admin_report/var
|
||||
ID // the ID of the report
|
||||
body // the content of the report
|
||||
author // key of the author
|
||||
date // date on which this was created
|
||||
done // whether this was handled
|
||||
|
||||
offender_key // store the key of the offender
|
||||
offender_cid // store the cid of the offender
|
||||
|
||||
/datum//report_topic_handler
|
||||
Topic(href,href_list)
|
||||
..()
|
||||
var/client/C = locate(href_list["client"])
|
||||
if(href_list["action"] == "show_reports")
|
||||
C.display_admin_reports()
|
||||
else if(href_list["action"] == "remove")
|
||||
C.mark_report_done(text2num(href_list["ID"]))
|
||||
else if(href_list["action"] == "edit")
|
||||
C.edit_report(text2num(href_list["ID"]))
|
||||
|
||||
var/datum/report_topic_handler/report_topic_handler
|
||||
|
||||
world/New()
|
||||
..()
|
||||
report_topic_handler = new
|
||||
|
||||
// add a new news datums
|
||||
/proc/make_report(body, author, okey, cid)
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
var/lastID
|
||||
|
||||
Reports["reports"] >> reports
|
||||
Reports["lastID"] >> lastID
|
||||
|
||||
if(!reports) reports = list()
|
||||
if(!lastID) lastID = 0
|
||||
|
||||
var/datum/admin_report/created = new()
|
||||
created.ID = ++lastID
|
||||
created.body = body
|
||||
created.author = author
|
||||
created.date = world.realtime
|
||||
created.done = 0
|
||||
created.offender_key = okey
|
||||
created.offender_cid = cid
|
||||
|
||||
reports.Insert(1, created)
|
||||
|
||||
Reports["reports"] << reports
|
||||
Reports["lastID"] << lastID
|
||||
|
||||
// load the reports from disk
|
||||
/proc/load_reports()
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
|
||||
Reports["reports"] >> reports
|
||||
|
||||
if(!reports) reports = list()
|
||||
|
||||
return reports
|
||||
|
||||
// check if there are any unhandled reports
|
||||
/client/proc/unhandled_reports()
|
||||
if(!src.holder) return 0
|
||||
var/list/reports = load_reports()
|
||||
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.done)
|
||||
continue
|
||||
else return 1
|
||||
|
||||
return 0
|
||||
|
||||
// checks if the player has an unhandled report against him
|
||||
/client/proc/is_reported()
|
||||
var/list/reports = load_reports()
|
||||
|
||||
for(var/datum/admin_report/N in reports) if(!N.done)
|
||||
if(N.offender_key == src.key)
|
||||
return 1
|
||||
|
||||
return 0
|
||||
|
||||
// display only the reports that haven't been handled
|
||||
/client/proc/display_admin_reports()
|
||||
set category = "Admin"
|
||||
set name = "Display Admin Reports"
|
||||
if(!src.holder) return
|
||||
|
||||
var/list/reports = load_reports()
|
||||
|
||||
var/output = ""
|
||||
if(unhandled_reports())
|
||||
// load the list of unhandled reports
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.done)
|
||||
continue
|
||||
output += "<b>Reported player:</b> [N.offender_key](CID: [N.offender_cid])<br>"
|
||||
output += "<b>Offense:</b>[N.body]<br>"
|
||||
output += "<small>Occurred at [time2text(N.date,"MM/DD hh:mm:ss")]</small><br>"
|
||||
output += "<small>authored by <i>[N.author]</i></small><br>"
|
||||
output += " <a href='?src=\ref[report_topic_handler];client=\ref[src];[HrefToken()];action=remove;ID=[N.ID]'>Flag as Handled</a>"
|
||||
if(src.key == N.author)
|
||||
output += " <a href='?src=\ref[report_topic_handler];client=\ref[src];[HrefToken()];action=edit;ID=[N.ID]'>Edit</a>"
|
||||
output += "<br>"
|
||||
output += "<br>"
|
||||
else
|
||||
output += "Whoops, no reports!"
|
||||
|
||||
usr << browse(output, "window=news;size=600x400")
|
||||
|
||||
|
||||
/client/proc/Report(mob/M as mob in world)
|
||||
set category = "Admin"
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
var/CID = "Unknown"
|
||||
if(M.client)
|
||||
CID = M.client.computer_id
|
||||
|
||||
var/body = tgui_input_text(src.mob, "Describe in detail what you're reporting [M] for", "Report")
|
||||
if(!body) return
|
||||
|
||||
|
||||
make_report(body, key, M.key, CID)
|
||||
|
||||
spawn(1)
|
||||
display_admin_reports()
|
||||
|
||||
/client/proc/mark_report_done(ID as num)
|
||||
if(!src.holder || src.holder.level < 0)
|
||||
return
|
||||
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
|
||||
Reports["reports"] >> reports
|
||||
|
||||
var/datum/admin_report/found
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.ID == ID)
|
||||
found = N
|
||||
if(!found)
|
||||
to_chat(src, "<b>* An error occurred, sorry.</b>")
|
||||
|
||||
found.done = 1
|
||||
|
||||
Reports["reports"] << reports
|
||||
|
||||
|
||||
/client/proc/edit_report(ID as num)
|
||||
if(!src.holder || src.holder.level < 0)
|
||||
to_chat(src, "<b>You tried to modify the news, but you're not an admin!</b>")
|
||||
return
|
||||
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
|
||||
Reports["reports"] >> reports
|
||||
|
||||
var/datum/admin_report/found
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.ID == ID)
|
||||
found = N
|
||||
if(!found)
|
||||
to_chat(src, "<b>* An error occurred, sorry.</b>")
|
||||
|
||||
var/body = tgui_input_text(src.mob, "Enter a body for the news", "Body", multiline = TRUE, prevent_enter = TRUE)
|
||||
if(!body) return
|
||||
|
||||
found.body = body
|
||||
|
||||
Reports["reports"] << reports
|
||||
// Reports are a way to notify admins of wrongdoings that happened
|
||||
// while no admin was present. They work a bit similar to news, but
|
||||
// they can only be read by admins and moderators.
|
||||
|
||||
// a single admin report
|
||||
/datum//admin_report/var
|
||||
ID // the ID of the report
|
||||
body // the content of the report
|
||||
author // key of the author
|
||||
date // date on which this was created
|
||||
done // whether this was handled
|
||||
|
||||
offender_key // store the key of the offender
|
||||
offender_cid // store the cid of the offender
|
||||
|
||||
/datum//report_topic_handler
|
||||
Topic(href,href_list)
|
||||
..()
|
||||
var/client/C = locate(href_list["client"])
|
||||
if(href_list["action"] == "show_reports")
|
||||
C.display_admin_reports()
|
||||
else if(href_list["action"] == "remove")
|
||||
C.mark_report_done(text2num(href_list["ID"]))
|
||||
else if(href_list["action"] == "edit")
|
||||
C.edit_report(text2num(href_list["ID"]))
|
||||
|
||||
var/datum/report_topic_handler/report_topic_handler
|
||||
|
||||
world/New()
|
||||
..()
|
||||
report_topic_handler = new
|
||||
|
||||
// add a new news datums
|
||||
/proc/make_report(body, author, okey, cid)
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
var/lastID
|
||||
|
||||
Reports["reports"] >> reports
|
||||
Reports["lastID"] >> lastID
|
||||
|
||||
if(!reports) reports = list()
|
||||
if(!lastID) lastID = 0
|
||||
|
||||
var/datum/admin_report/created = new()
|
||||
created.ID = ++lastID
|
||||
created.body = body
|
||||
created.author = author
|
||||
created.date = world.realtime
|
||||
created.done = 0
|
||||
created.offender_key = okey
|
||||
created.offender_cid = cid
|
||||
|
||||
reports.Insert(1, created)
|
||||
|
||||
Reports["reports"] << reports
|
||||
Reports["lastID"] << lastID
|
||||
|
||||
// load the reports from disk
|
||||
/proc/load_reports()
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
|
||||
Reports["reports"] >> reports
|
||||
|
||||
if(!reports) reports = list()
|
||||
|
||||
return reports
|
||||
|
||||
// check if there are any unhandled reports
|
||||
/client/proc/unhandled_reports()
|
||||
if(!src.holder) return 0
|
||||
var/list/reports = load_reports()
|
||||
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.done)
|
||||
continue
|
||||
else return 1
|
||||
|
||||
return 0
|
||||
|
||||
// checks if the player has an unhandled report against him
|
||||
/client/proc/is_reported()
|
||||
var/list/reports = load_reports()
|
||||
|
||||
for(var/datum/admin_report/N in reports) if(!N.done)
|
||||
if(N.offender_key == src.key)
|
||||
return 1
|
||||
|
||||
return 0
|
||||
|
||||
// display only the reports that haven't been handled
|
||||
/client/proc/display_admin_reports()
|
||||
set category = "Admin"
|
||||
set name = "Display Admin Reports"
|
||||
if(!src.holder) return
|
||||
|
||||
var/list/reports = load_reports()
|
||||
|
||||
var/output = ""
|
||||
if(unhandled_reports())
|
||||
// load the list of unhandled reports
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.done)
|
||||
continue
|
||||
output += "<b>Reported player:</b> [N.offender_key](CID: [N.offender_cid])<br>"
|
||||
output += "<b>Offense:</b>[N.body]<br>"
|
||||
output += "<small>Occurred at [time2text(N.date,"MM/DD hh:mm:ss")]</small><br>"
|
||||
output += "<small>authored by <i>[N.author]</i></small><br>"
|
||||
output += " <a href='?src=\ref[report_topic_handler];client=\ref[src];[HrefToken()];action=remove;ID=[N.ID]'>Flag as Handled</a>"
|
||||
if(src.key == N.author)
|
||||
output += " <a href='?src=\ref[report_topic_handler];client=\ref[src];[HrefToken()];action=edit;ID=[N.ID]'>Edit</a>"
|
||||
output += "<br>"
|
||||
output += "<br>"
|
||||
else
|
||||
output += "Whoops, no reports!"
|
||||
|
||||
usr << browse(output, "window=news;size=600x400")
|
||||
|
||||
|
||||
/client/proc/Report(mob/M as mob in world)
|
||||
set category = "Admin"
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
var/CID = "Unknown"
|
||||
if(M.client)
|
||||
CID = M.client.computer_id
|
||||
|
||||
var/body = tgui_input_text(src.mob, "Describe in detail what you're reporting [M] for", "Report")
|
||||
if(!body) return
|
||||
|
||||
|
||||
make_report(body, key, M.key, CID)
|
||||
|
||||
spawn(1)
|
||||
display_admin_reports()
|
||||
|
||||
/client/proc/mark_report_done(ID as num)
|
||||
if(!src.holder || src.holder.level < 0)
|
||||
return
|
||||
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
|
||||
Reports["reports"] >> reports
|
||||
|
||||
var/datum/admin_report/found
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.ID == ID)
|
||||
found = N
|
||||
if(!found)
|
||||
to_chat(src, "<b>* An error occurred, sorry.</b>")
|
||||
|
||||
found.done = 1
|
||||
|
||||
Reports["reports"] << reports
|
||||
|
||||
|
||||
/client/proc/edit_report(ID as num)
|
||||
if(!src.holder || src.holder.level < 0)
|
||||
to_chat(src, "<b>You tried to modify the news, but you're not an admin!</b>")
|
||||
return
|
||||
|
||||
var/savefile/Reports = new("data/reports.sav")
|
||||
var/list/reports
|
||||
|
||||
Reports["reports"] >> reports
|
||||
|
||||
var/datum/admin_report/found
|
||||
for(var/datum/admin_report/N in reports)
|
||||
if(N.ID == ID)
|
||||
found = N
|
||||
if(!found)
|
||||
to_chat(src, "<b>* An error occurred, sorry.</b>")
|
||||
|
||||
var/body = tgui_input_text(src.mob, "Enter a body for the news", "Body", multiline = TRUE, prevent_enter = TRUE)
|
||||
if(!body) return
|
||||
|
||||
found.body = body
|
||||
|
||||
Reports["reports"] << reports
|
||||
|
||||
+113
-113
@@ -1,113 +1,113 @@
|
||||
var/datum/admin_secrets/admin_secrets = new()
|
||||
|
||||
/datum/admin_secrets
|
||||
var/list/datum/admin_secret_category/categories
|
||||
var/list/datum/admin_secret_item/items
|
||||
|
||||
/datum/admin_secrets/New()
|
||||
..()
|
||||
categories = init_subtypes(/datum/admin_secret_category)
|
||||
items = list()
|
||||
var/list/category_assoc = list()
|
||||
for(var/datum/admin_secret_category/category in categories)
|
||||
category_assoc[category.type] = category
|
||||
|
||||
for(var/item_type in subtypesof(/datum/admin_secret_item))
|
||||
var/datum/admin_secret_item/secret_item = item_type
|
||||
if(!initial(secret_item.name))
|
||||
continue
|
||||
|
||||
var/datum/admin_secret_item/item = new item_type()
|
||||
var/datum/admin_secret_category/category = category_assoc[item.category]
|
||||
dd_insertObjectList(category.items, item)
|
||||
items += item
|
||||
|
||||
//
|
||||
// Secret Item Category - Each subtype is a category for organizing secret commands.
|
||||
//
|
||||
/datum/admin_secret_category
|
||||
var/name = ""
|
||||
var/desc = ""
|
||||
var/list/datum/admin_secret_item/items = list()
|
||||
|
||||
/datum/admin_secret_category/proc/can_view(var/mob/user)
|
||||
for(var/datum/admin_secret_item/item in items)
|
||||
if(item.can_view(user))
|
||||
return 1
|
||||
return 0
|
||||
|
||||
//
|
||||
// Secret Item Datum - Each subtype is a command on the secrets panel.
|
||||
// Override execute() with the implementation of the command.
|
||||
//
|
||||
/datum/admin_secret_item
|
||||
var/name = ""
|
||||
var/category = null
|
||||
var/log = 1
|
||||
var/feedback = 1
|
||||
var/permissions = R_HOST
|
||||
var/warn_before_use = 0
|
||||
|
||||
/datum/admin_secret_item/dd_SortValue()
|
||||
return "[name]"
|
||||
|
||||
/datum/admin_secret_item/proc/name()
|
||||
return name
|
||||
|
||||
/datum/admin_secret_item/proc/can_view(var/mob/user)
|
||||
return check_rights(permissions, 0, user)
|
||||
|
||||
/datum/admin_secret_item/proc/can_execute(var/mob/user)
|
||||
if(can_view(user))
|
||||
if(!warn_before_use || tgui_alert(usr, "Execute the command '[name]'?", name, list("No","Yes")) == "Yes")
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/datum/admin_secret_item/proc/execute(var/mob/user)
|
||||
if(!can_execute(user))
|
||||
return 0
|
||||
|
||||
if(log)
|
||||
log_and_message_admins("used secret '[name]'", user)
|
||||
if(feedback)
|
||||
feedback_inc("admin_secrets_used",1)
|
||||
feedback_add_details("admin_secrets_used","[name]")
|
||||
return 1
|
||||
|
||||
/*************************
|
||||
* Pre-defined categories *
|
||||
*************************/
|
||||
/datum/admin_secret_category/admin_secrets
|
||||
name = "Admin Secrets"
|
||||
|
||||
/datum/admin_secret_category/random_events
|
||||
name = "'Random' Events"
|
||||
|
||||
/datum/admin_secret_category/fun_secrets
|
||||
name = "Fun Secrets"
|
||||
|
||||
/datum/admin_secret_category/final_solutions
|
||||
name = "Final Solutions"
|
||||
desc = "(Warning, these will end the round!)"
|
||||
|
||||
/*************************
|
||||
* Pre-defined base items *
|
||||
*************************/
|
||||
/datum/admin_secret_item/admin_secret
|
||||
category = /datum/admin_secret_category/admin_secrets
|
||||
log = 0
|
||||
permissions = R_ADMIN //VOREStation Edit
|
||||
|
||||
/datum/admin_secret_item/random_event
|
||||
category = /datum/admin_secret_category/random_events
|
||||
permissions = R_FUN //VOREStation Edit
|
||||
warn_before_use = 1
|
||||
|
||||
/datum/admin_secret_item/fun_secret
|
||||
category = /datum/admin_secret_category/fun_secrets
|
||||
permissions = R_FUN //VOREStation Edit
|
||||
warn_before_use = 1
|
||||
|
||||
/datum/admin_secret_item/final_solution
|
||||
category = /datum/admin_secret_category/final_solutions
|
||||
permissions = R_FUN|R_SERVER|R_ADMIN //VOREStation Edit
|
||||
var/datum/admin_secrets/admin_secrets = new()
|
||||
|
||||
/datum/admin_secrets
|
||||
var/list/datum/admin_secret_category/categories
|
||||
var/list/datum/admin_secret_item/items
|
||||
|
||||
/datum/admin_secrets/New()
|
||||
..()
|
||||
categories = init_subtypes(/datum/admin_secret_category)
|
||||
items = list()
|
||||
var/list/category_assoc = list()
|
||||
for(var/datum/admin_secret_category/category in categories)
|
||||
category_assoc[category.type] = category
|
||||
|
||||
for(var/item_type in subtypesof(/datum/admin_secret_item))
|
||||
var/datum/admin_secret_item/secret_item = item_type
|
||||
if(!initial(secret_item.name))
|
||||
continue
|
||||
|
||||
var/datum/admin_secret_item/item = new item_type()
|
||||
var/datum/admin_secret_category/category = category_assoc[item.category]
|
||||
dd_insertObjectList(category.items, item)
|
||||
items += item
|
||||
|
||||
//
|
||||
// Secret Item Category - Each subtype is a category for organizing secret commands.
|
||||
//
|
||||
/datum/admin_secret_category
|
||||
var/name = ""
|
||||
var/desc = ""
|
||||
var/list/datum/admin_secret_item/items = list()
|
||||
|
||||
/datum/admin_secret_category/proc/can_view(var/mob/user)
|
||||
for(var/datum/admin_secret_item/item in items)
|
||||
if(item.can_view(user))
|
||||
return 1
|
||||
return 0
|
||||
|
||||
//
|
||||
// Secret Item Datum - Each subtype is a command on the secrets panel.
|
||||
// Override execute() with the implementation of the command.
|
||||
//
|
||||
/datum/admin_secret_item
|
||||
var/name = ""
|
||||
var/category = null
|
||||
var/log = 1
|
||||
var/feedback = 1
|
||||
var/permissions = R_HOST
|
||||
var/warn_before_use = 0
|
||||
|
||||
/datum/admin_secret_item/dd_SortValue()
|
||||
return "[name]"
|
||||
|
||||
/datum/admin_secret_item/proc/name()
|
||||
return name
|
||||
|
||||
/datum/admin_secret_item/proc/can_view(var/mob/user)
|
||||
return check_rights(permissions, 0, user)
|
||||
|
||||
/datum/admin_secret_item/proc/can_execute(var/mob/user)
|
||||
if(can_view(user))
|
||||
if(!warn_before_use || tgui_alert(usr, "Execute the command '[name]'?", name, list("No","Yes")) == "Yes")
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/datum/admin_secret_item/proc/execute(var/mob/user)
|
||||
if(!can_execute(user))
|
||||
return 0
|
||||
|
||||
if(log)
|
||||
log_and_message_admins("used secret '[name]'", user)
|
||||
if(feedback)
|
||||
feedback_inc("admin_secrets_used",1)
|
||||
feedback_add_details("admin_secrets_used","[name]")
|
||||
return 1
|
||||
|
||||
/*************************
|
||||
* Pre-defined categories *
|
||||
*************************/
|
||||
/datum/admin_secret_category/admin_secrets
|
||||
name = "Admin Secrets"
|
||||
|
||||
/datum/admin_secret_category/random_events
|
||||
name = "'Random' Events"
|
||||
|
||||
/datum/admin_secret_category/fun_secrets
|
||||
name = "Fun Secrets"
|
||||
|
||||
/datum/admin_secret_category/final_solutions
|
||||
name = "Final Solutions"
|
||||
desc = "(Warning, these will end the round!)"
|
||||
|
||||
/*************************
|
||||
* Pre-defined base items *
|
||||
*************************/
|
||||
/datum/admin_secret_item/admin_secret
|
||||
category = /datum/admin_secret_category/admin_secrets
|
||||
log = 0
|
||||
permissions = R_ADMIN //VOREStation Edit
|
||||
|
||||
/datum/admin_secret_item/random_event
|
||||
category = /datum/admin_secret_category/random_events
|
||||
permissions = R_FUN //VOREStation Edit
|
||||
warn_before_use = 1
|
||||
|
||||
/datum/admin_secret_item/fun_secret
|
||||
category = /datum/admin_secret_category/fun_secrets
|
||||
permissions = R_FUN //VOREStation Edit
|
||||
warn_before_use = 1
|
||||
|
||||
/datum/admin_secret_item/final_solution
|
||||
category = /datum/admin_secret_category/final_solutions
|
||||
permissions = R_FUN|R_SERVER|R_ADMIN //VOREStation Edit
|
||||
|
||||
+561
-561
File diff suppressed because it is too large
Load Diff
+118
-118
@@ -1,118 +1,118 @@
|
||||
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:32
|
||||
|
||||
var/jobban_runonce // Updates legacy bans with new info
|
||||
var/jobban_keylist[0] //to store the keys & ranks
|
||||
|
||||
/proc/jobban_fullban(mob/M, rank, reason)
|
||||
if (!M || !M.key) return
|
||||
jobban_keylist.Add(text("[M.ckey] - [rank] ## [reason]"))
|
||||
jobban_savebanfile()
|
||||
|
||||
/proc/jobban_client_fullban(ckey, rank)
|
||||
if (!ckey || !rank) return
|
||||
jobban_keylist.Add(text("[ckey] - [rank]"))
|
||||
jobban_savebanfile()
|
||||
|
||||
//returns a reason if M is banned from rank, returns 0 otherwise
|
||||
/proc/jobban_isbanned(mob/M, rank)
|
||||
if(M && rank)
|
||||
/*
|
||||
if(_jobban_isbanned(M, rank)) return "Reason Unspecified" //for old jobban
|
||||
*/
|
||||
|
||||
if (guest_jobbans(rank))
|
||||
if(config.guest_jobban && IsGuestKey(M.key))
|
||||
return "Guest Job-ban"
|
||||
if(config.usewhitelist && !check_whitelist(M))
|
||||
return "Whitelisted Job"
|
||||
|
||||
return ckey_is_jobbanned(M.ckey, rank)
|
||||
return 0
|
||||
|
||||
/proc/ckey_is_jobbanned(var/check_key, var/rank)
|
||||
for(var/s in jobban_keylist)
|
||||
if(findtext(s,"[check_key] - [rank]") == 1 )
|
||||
var/startpos = findtext(s, "## ")+3
|
||||
if(startpos && startpos<length(s))
|
||||
var/text = copytext(s, startpos, 0)
|
||||
if(text)
|
||||
return text
|
||||
return "Reason Unspecified"
|
||||
return 0
|
||||
|
||||
/*
|
||||
DEBUG
|
||||
/mob/verb/list_all_jobbans()
|
||||
set name = "list all jobbans"
|
||||
|
||||
for(var/s in jobban_keylist)
|
||||
to_world(s)
|
||||
|
||||
/mob/verb/reload_jobbans()
|
||||
set name = "reload jobbans"
|
||||
|
||||
jobban_loadbanfile()
|
||||
*/
|
||||
|
||||
/hook/startup/proc/loadJobBans()
|
||||
jobban_loadbanfile()
|
||||
return 1
|
||||
|
||||
/proc/jobban_loadbanfile()
|
||||
if(config.ban_legacy_system)
|
||||
var/savefile/S=new("data/job_full.ban")
|
||||
S["keys[0]"] >> jobban_keylist
|
||||
log_admin("Loading jobban_rank")
|
||||
S["runonce"] >> jobban_runonce
|
||||
|
||||
if (!length(jobban_keylist))
|
||||
jobban_keylist=list()
|
||||
log_admin("jobban_keylist was empty")
|
||||
else
|
||||
if(!establish_db_connection())
|
||||
error("Database connection failed. Reverting to the legacy ban system.")
|
||||
log_misc("Database connection failed. Reverting to the legacy ban system.")
|
||||
config.ban_legacy_system = 1
|
||||
jobban_loadbanfile()
|
||||
return
|
||||
|
||||
//Job permabans
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT ckey, job FROM erro_ban WHERE bantype = 'JOB_PERMABAN' AND isnull(unbanned)")
|
||||
query.Execute()
|
||||
|
||||
while(query.NextRow())
|
||||
var/ckey = query.item[1]
|
||||
var/job = query.item[2]
|
||||
|
||||
jobban_keylist.Add("[ckey] - [job]")
|
||||
|
||||
//Job tempbans
|
||||
var/DBQuery/query1 = dbcon.NewQuery("SELECT ckey, job FROM erro_ban WHERE bantype = 'JOB_TEMPBAN' AND isnull(unbanned) AND expiration_time > Now()")
|
||||
query1.Execute()
|
||||
|
||||
while(query1.NextRow())
|
||||
var/ckey = query1.item[1]
|
||||
var/job = query1.item[2]
|
||||
|
||||
jobban_keylist.Add("[ckey] - [job]")
|
||||
|
||||
/proc/jobban_savebanfile()
|
||||
var/savefile/S=new("data/job_full.ban")
|
||||
S["keys[0]"] << jobban_keylist
|
||||
|
||||
/proc/jobban_unban(mob/M, rank)
|
||||
jobban_remove("[M.ckey] - [rank]")
|
||||
jobban_savebanfile()
|
||||
|
||||
|
||||
/proc/ban_unban_log_save(var/formatted_log)
|
||||
text2file(formatted_log,"data/ban_unban_log.txt")
|
||||
|
||||
|
||||
/proc/jobban_remove(X)
|
||||
for (var/i = 1; i <= length(jobban_keylist); i++)
|
||||
if( findtext(jobban_keylist[i], "[X]") )
|
||||
jobban_keylist.Remove(jobban_keylist[i])
|
||||
jobban_savebanfile()
|
||||
return 1
|
||||
return 0
|
||||
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:32
|
||||
|
||||
var/jobban_runonce // Updates legacy bans with new info
|
||||
var/jobban_keylist[0] //to store the keys & ranks
|
||||
|
||||
/proc/jobban_fullban(mob/M, rank, reason)
|
||||
if (!M || !M.key) return
|
||||
jobban_keylist.Add(text("[M.ckey] - [rank] ## [reason]"))
|
||||
jobban_savebanfile()
|
||||
|
||||
/proc/jobban_client_fullban(ckey, rank)
|
||||
if (!ckey || !rank) return
|
||||
jobban_keylist.Add(text("[ckey] - [rank]"))
|
||||
jobban_savebanfile()
|
||||
|
||||
//returns a reason if M is banned from rank, returns 0 otherwise
|
||||
/proc/jobban_isbanned(mob/M, rank)
|
||||
if(M && rank)
|
||||
/*
|
||||
if(_jobban_isbanned(M, rank)) return "Reason Unspecified" //for old jobban
|
||||
*/
|
||||
|
||||
if (guest_jobbans(rank))
|
||||
if(config.guest_jobban && IsGuestKey(M.key))
|
||||
return "Guest Job-ban"
|
||||
if(config.usewhitelist && !check_whitelist(M))
|
||||
return "Whitelisted Job"
|
||||
|
||||
return ckey_is_jobbanned(M.ckey, rank)
|
||||
return 0
|
||||
|
||||
/proc/ckey_is_jobbanned(var/check_key, var/rank)
|
||||
for(var/s in jobban_keylist)
|
||||
if(findtext(s,"[check_key] - [rank]") == 1 )
|
||||
var/startpos = findtext(s, "## ")+3
|
||||
if(startpos && startpos<length(s))
|
||||
var/text = copytext(s, startpos, 0)
|
||||
if(text)
|
||||
return text
|
||||
return "Reason Unspecified"
|
||||
return 0
|
||||
|
||||
/*
|
||||
DEBUG
|
||||
/mob/verb/list_all_jobbans()
|
||||
set name = "list all jobbans"
|
||||
|
||||
for(var/s in jobban_keylist)
|
||||
to_world(s)
|
||||
|
||||
/mob/verb/reload_jobbans()
|
||||
set name = "reload jobbans"
|
||||
|
||||
jobban_loadbanfile()
|
||||
*/
|
||||
|
||||
/hook/startup/proc/loadJobBans()
|
||||
jobban_loadbanfile()
|
||||
return 1
|
||||
|
||||
/proc/jobban_loadbanfile()
|
||||
if(config.ban_legacy_system)
|
||||
var/savefile/S=new("data/job_full.ban")
|
||||
S["keys[0]"] >> jobban_keylist
|
||||
log_admin("Loading jobban_rank")
|
||||
S["runonce"] >> jobban_runonce
|
||||
|
||||
if (!length(jobban_keylist))
|
||||
jobban_keylist=list()
|
||||
log_admin("jobban_keylist was empty")
|
||||
else
|
||||
if(!establish_db_connection())
|
||||
error("Database connection failed. Reverting to the legacy ban system.")
|
||||
log_misc("Database connection failed. Reverting to the legacy ban system.")
|
||||
config.ban_legacy_system = 1
|
||||
jobban_loadbanfile()
|
||||
return
|
||||
|
||||
//Job permabans
|
||||
var/DBQuery/query = dbcon.NewQuery("SELECT ckey, job FROM erro_ban WHERE bantype = 'JOB_PERMABAN' AND isnull(unbanned)")
|
||||
query.Execute()
|
||||
|
||||
while(query.NextRow())
|
||||
var/ckey = query.item[1]
|
||||
var/job = query.item[2]
|
||||
|
||||
jobban_keylist.Add("[ckey] - [job]")
|
||||
|
||||
//Job tempbans
|
||||
var/DBQuery/query1 = dbcon.NewQuery("SELECT ckey, job FROM erro_ban WHERE bantype = 'JOB_TEMPBAN' AND isnull(unbanned) AND expiration_time > Now()")
|
||||
query1.Execute()
|
||||
|
||||
while(query1.NextRow())
|
||||
var/ckey = query1.item[1]
|
||||
var/job = query1.item[2]
|
||||
|
||||
jobban_keylist.Add("[ckey] - [job]")
|
||||
|
||||
/proc/jobban_savebanfile()
|
||||
var/savefile/S=new("data/job_full.ban")
|
||||
S["keys[0]"] << jobban_keylist
|
||||
|
||||
/proc/jobban_unban(mob/M, rank)
|
||||
jobban_remove("[M.ckey] - [rank]")
|
||||
jobban_savebanfile()
|
||||
|
||||
|
||||
/proc/ban_unban_log_save(var/formatted_log)
|
||||
text2file(formatted_log,"data/ban_unban_log.txt")
|
||||
|
||||
|
||||
/proc/jobban_remove(X)
|
||||
for (var/i = 1; i <= length(jobban_keylist); i++)
|
||||
if( findtext(jobban_keylist[i], "[X]") )
|
||||
jobban_keylist.Remove(jobban_keylist[i])
|
||||
jobban_savebanfile()
|
||||
return 1
|
||||
return 0
|
||||
|
||||
@@ -1,210 +1,210 @@
|
||||
/client/proc/callproc()
|
||||
set category = "Debug"
|
||||
set name = "Advanced ProcCall"
|
||||
set waitfor = 0
|
||||
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
|
||||
var/datum/target = null
|
||||
var/targetselected = 0
|
||||
var/returnval = null
|
||||
|
||||
switch(tgui_alert(usr, "Proc owned by something?","Call Proc",list("Yes","No")))
|
||||
if("Yes")
|
||||
targetselected = 1
|
||||
var/list/value = vv_get_value(default_class = VV_ATOM_REFERENCE, classes = list(VV_ATOM_REFERENCE, VV_DATUM_REFERENCE, VV_MOB_REFERENCE, VV_CLIENT))
|
||||
if (!value["class"] || !value["value"])
|
||||
return
|
||||
target = value["value"]
|
||||
if("No")
|
||||
target = null
|
||||
targetselected = 0
|
||||
|
||||
var/procname = tgui_input_text(usr, "Proc path, eg: /proc/fake_blood","Path:", null)
|
||||
if(!procname)
|
||||
return
|
||||
|
||||
//hascall() doesn't support proc paths (eg: /proc/gib(), it only supports "gib")
|
||||
var/testname = procname
|
||||
if(targetselected)
|
||||
//Find one of the 3 possible ways they could have written /proc/PROCNAME
|
||||
if(findtext(procname, "/proc/"))
|
||||
testname = replacetext(procname, "/proc/", "")
|
||||
else if(findtext(procname, "/proc"))
|
||||
testname = replacetext(procname, "/proc", "")
|
||||
else if(findtext(procname, "proc/"))
|
||||
testname = replacetext(procname, "proc/", "")
|
||||
//Clear out any parenthesis if they're a dummy
|
||||
testname = replacetext(testname, "()", "")
|
||||
|
||||
if(targetselected && !hascall(target,testname))
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc(): type [target.type] has no proc named [procname].") + "</span>")
|
||||
return
|
||||
else
|
||||
var/procpath = text2path(procname)
|
||||
if (!procpath)
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc(): proc [procname] does not exist. (Did you forget the /proc/ part?)") + "</span>")
|
||||
return
|
||||
var/list/lst = get_callproc_args()
|
||||
if(!lst)
|
||||
return
|
||||
|
||||
if(targetselected)
|
||||
if(!target)
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc(): owner of proc no longer exists.") + "</span>")
|
||||
return
|
||||
var/msg = "[key_name(src)] called [target]'s [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"]."
|
||||
log_admin(msg)
|
||||
//message_admins(msg) //Proccall announce removed.
|
||||
admin_ticket_log(target, msg)
|
||||
returnval = WrapAdminProcCall(target, procname, lst) // Pass the lst as an argument list to the proc
|
||||
else
|
||||
//this currently has no hascall protection. wasn't able to get it working.
|
||||
log_admin("[key_name(src)] called [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"].")
|
||||
//message_admins("[key_name(src)] called [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"].") //Proccall announce removed.
|
||||
returnval = WrapAdminProcCall(GLOBAL_PROC, procname, lst) // Pass the lst as an argument list to the proc
|
||||
. = get_callproc_returnval(returnval, procname)
|
||||
if(.)
|
||||
to_chat(usr, .)
|
||||
feedback_add_details("admin_verb","APC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
GLOBAL_VAR(AdminProcCaller)
|
||||
GLOBAL_PROTECT(AdminProcCaller)
|
||||
GLOBAL_VAR_INIT(AdminProcCallCount, 0)
|
||||
GLOBAL_PROTECT(AdminProcCallCount)
|
||||
GLOBAL_VAR(LastAdminCalledTargetRef)
|
||||
GLOBAL_PROTECT(LastAdminCalledTargetRef)
|
||||
GLOBAL_VAR(LastAdminCalledTarget)
|
||||
GLOBAL_PROTECT(LastAdminCalledTarget)
|
||||
GLOBAL_VAR(LastAdminCalledProc)
|
||||
GLOBAL_PROTECT(LastAdminCalledProc)
|
||||
GLOBAL_LIST_EMPTY(AdminProcCallSpamPrevention)
|
||||
GLOBAL_PROTECT(AdminProcCallSpamPrevention)
|
||||
|
||||
/proc/WrapAdminProcCall(datum/target, procname, list/arguments)
|
||||
if(target && procname == "Del")
|
||||
to_chat(usr, "<span class='filter_adminlog'>Calling Del() is not allowed</span>")
|
||||
return
|
||||
|
||||
if(target != GLOBAL_PROC && !target.CanProcCall(procname))
|
||||
to_chat(usr, "<span class='filter_adminlog'>Proccall on [target.type]/proc/[procname] is disallowed!</span>")
|
||||
return
|
||||
var/current_caller = GLOB.AdminProcCaller
|
||||
var/ckey = usr ? usr.client.ckey : GLOB.AdminProcCaller
|
||||
if(!ckey)
|
||||
CRASH("WrapAdminProcCall with no ckey: [target] [procname] [english_list(arguments)]")
|
||||
if(current_caller && current_caller != ckey)
|
||||
if(!GLOB.AdminProcCallSpamPrevention[ckey])
|
||||
to_chat(usr, "<span class='adminnotice'>Another set of admin called procs are still running, your proc will be run after theirs finish.</span>")
|
||||
GLOB.AdminProcCallSpamPrevention[ckey] = TRUE
|
||||
UNTIL(!GLOB.AdminProcCaller)
|
||||
to_chat(usr, "<span class='adminnotice'>Running your proc</span>")
|
||||
GLOB.AdminProcCallSpamPrevention -= ckey
|
||||
else
|
||||
UNTIL(!GLOB.AdminProcCaller)
|
||||
GLOB.LastAdminCalledProc = procname
|
||||
if(target != GLOBAL_PROC)
|
||||
GLOB.LastAdminCalledTargetRef = "\ref[target]"
|
||||
GLOB.AdminProcCaller = ckey //if this runtimes, too bad for you
|
||||
++GLOB.AdminProcCallCount
|
||||
. = world.WrapAdminProcCall(target, procname, arguments)
|
||||
if(--GLOB.AdminProcCallCount == 0)
|
||||
GLOB.AdminProcCaller = null
|
||||
|
||||
//adv proc call this, ya nerds
|
||||
/world/proc/WrapAdminProcCall(datum/target, procname, list/arguments)
|
||||
if(target == GLOBAL_PROC)
|
||||
return call(procname)(arglist(arguments))
|
||||
else if(target != world)
|
||||
return call(target, procname)(arglist(arguments))
|
||||
else
|
||||
log_admin("[key_name(usr)] attempted to call world/proc/[procname] with arguments: [english_list(arguments)]")
|
||||
|
||||
/proc/IsAdminAdvancedProcCall()
|
||||
#ifdef TESTING
|
||||
return FALSE
|
||||
#else
|
||||
return usr && usr.client && GLOB.AdminProcCaller == usr.client.ckey
|
||||
#endif
|
||||
|
||||
/client/proc/callproc_datum(datum/A as null|area|mob|obj|turf)
|
||||
set category = "Debug"
|
||||
set name = "Atom ProcCall"
|
||||
set waitfor = 0
|
||||
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
|
||||
var/procname = tgui_input_text(usr, "Proc name, eg: fake_blood","Proc:", null)
|
||||
if(!procname)
|
||||
return
|
||||
if(!hascall(A,procname))
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc_datum(): type [A.type] has no proc named [procname].") + "</span>")
|
||||
return
|
||||
var/list/lst = get_callproc_args()
|
||||
if(!lst)
|
||||
return
|
||||
|
||||
if(!A || !IsValidSrc(A))
|
||||
to_chat(usr, "<span class='warning'>Error: callproc_datum(): owner of proc no longer exists.</span>")
|
||||
return
|
||||
var/msg = "[key_name(src)] called [A]'s [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"]."
|
||||
log_admin(msg)
|
||||
//message_admins(msg)
|
||||
admin_ticket_log(A, msg)
|
||||
feedback_add_details("admin_verb","TPC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
var/returnval = WrapAdminProcCall(A, procname, lst) // Pass the lst as an argument list to the proc
|
||||
. = get_callproc_returnval(returnval,procname)
|
||||
if(.)
|
||||
to_chat(usr, .)
|
||||
|
||||
/client/proc/get_callproc_args()
|
||||
var/argnum = tgui_input_number(usr, "Number of arguments","Number:",0)
|
||||
if(isnull(argnum))
|
||||
return null //Cancel
|
||||
|
||||
. = list()
|
||||
//var/list/named_args = list() //Named arguments are removed, due to them making proccalling take too long.
|
||||
while(argnum--)
|
||||
/* //Named arguments are removed, due to them making proccalling take too long.
|
||||
var/named_arg = input(usr,"Leave blank for positional argument. Positional arguments will be considered as if they were added first.", "Named argument") as text|null
|
||||
if(isnull(named_arg))
|
||||
return null //Cancel
|
||||
*/
|
||||
var/value = vv_get_value(restricted_classes = list(VV_RESTORE_DEFAULT))
|
||||
if (!value["class"])
|
||||
return null //Cancel
|
||||
/* //Named arguments are removed, due to them making proccalling take too long.
|
||||
if(named_arg)
|
||||
named_args[named_arg] = value["value"]
|
||||
else
|
||||
. += value["value"]
|
||||
if(LAZYLEN(named_args))
|
||||
. += named_args
|
||||
*/
|
||||
. += value["value"]
|
||||
|
||||
/client/proc/get_callproc_returnval(returnval,procname)
|
||||
. = ""
|
||||
if(islist(returnval))
|
||||
var/list/returnedlist = returnval
|
||||
. = "<span class='blue'>"
|
||||
if(returnedlist.len)
|
||||
var/assoc_check = returnedlist[1]
|
||||
if(istext(assoc_check) && (returnedlist[assoc_check] != null))
|
||||
. += "[procname] returned an associative list:"
|
||||
for(var/key in returnedlist)
|
||||
. += "\n[key] = [returnedlist[key]]"
|
||||
|
||||
else
|
||||
. += "[procname] returned a list:"
|
||||
for(var/elem in returnedlist)
|
||||
. += "\n[elem]"
|
||||
else
|
||||
. = "[procname] returned an empty list"
|
||||
. += "</span>"
|
||||
|
||||
else
|
||||
. = span_blue("[procname] returned: [!isnull(returnval) ? returnval : "null"]")
|
||||
/client/proc/callproc()
|
||||
set category = "Debug"
|
||||
set name = "Advanced ProcCall"
|
||||
set waitfor = 0
|
||||
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
|
||||
var/datum/target = null
|
||||
var/targetselected = 0
|
||||
var/returnval = null
|
||||
|
||||
switch(tgui_alert(usr, "Proc owned by something?","Call Proc",list("Yes","No")))
|
||||
if("Yes")
|
||||
targetselected = 1
|
||||
var/list/value = vv_get_value(default_class = VV_ATOM_REFERENCE, classes = list(VV_ATOM_REFERENCE, VV_DATUM_REFERENCE, VV_MOB_REFERENCE, VV_CLIENT))
|
||||
if (!value["class"] || !value["value"])
|
||||
return
|
||||
target = value["value"]
|
||||
if("No")
|
||||
target = null
|
||||
targetselected = 0
|
||||
|
||||
var/procname = tgui_input_text(usr, "Proc path, eg: /proc/fake_blood","Path:", null)
|
||||
if(!procname)
|
||||
return
|
||||
|
||||
//hascall() doesn't support proc paths (eg: /proc/gib(), it only supports "gib")
|
||||
var/testname = procname
|
||||
if(targetselected)
|
||||
//Find one of the 3 possible ways they could have written /proc/PROCNAME
|
||||
if(findtext(procname, "/proc/"))
|
||||
testname = replacetext(procname, "/proc/", "")
|
||||
else if(findtext(procname, "/proc"))
|
||||
testname = replacetext(procname, "/proc", "")
|
||||
else if(findtext(procname, "proc/"))
|
||||
testname = replacetext(procname, "proc/", "")
|
||||
//Clear out any parenthesis if they're a dummy
|
||||
testname = replacetext(testname, "()", "")
|
||||
|
||||
if(targetselected && !hascall(target,testname))
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc(): type [target.type] has no proc named [procname].") + "</span>")
|
||||
return
|
||||
else
|
||||
var/procpath = text2path(procname)
|
||||
if (!procpath)
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc(): proc [procname] does not exist. (Did you forget the /proc/ part?)") + "</span>")
|
||||
return
|
||||
var/list/lst = get_callproc_args()
|
||||
if(!lst)
|
||||
return
|
||||
|
||||
if(targetselected)
|
||||
if(!target)
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc(): owner of proc no longer exists.") + "</span>")
|
||||
return
|
||||
var/msg = "[key_name(src)] called [target]'s [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"]."
|
||||
log_admin(msg)
|
||||
//message_admins(msg) //Proccall announce removed.
|
||||
admin_ticket_log(target, msg)
|
||||
returnval = WrapAdminProcCall(target, procname, lst) // Pass the lst as an argument list to the proc
|
||||
else
|
||||
//this currently has no hascall protection. wasn't able to get it working.
|
||||
log_admin("[key_name(src)] called [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"].")
|
||||
//message_admins("[key_name(src)] called [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"].") //Proccall announce removed.
|
||||
returnval = WrapAdminProcCall(GLOBAL_PROC, procname, lst) // Pass the lst as an argument list to the proc
|
||||
. = get_callproc_returnval(returnval, procname)
|
||||
if(.)
|
||||
to_chat(usr, .)
|
||||
feedback_add_details("admin_verb","APC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
GLOBAL_VAR(AdminProcCaller)
|
||||
GLOBAL_PROTECT(AdminProcCaller)
|
||||
GLOBAL_VAR_INIT(AdminProcCallCount, 0)
|
||||
GLOBAL_PROTECT(AdminProcCallCount)
|
||||
GLOBAL_VAR(LastAdminCalledTargetRef)
|
||||
GLOBAL_PROTECT(LastAdminCalledTargetRef)
|
||||
GLOBAL_VAR(LastAdminCalledTarget)
|
||||
GLOBAL_PROTECT(LastAdminCalledTarget)
|
||||
GLOBAL_VAR(LastAdminCalledProc)
|
||||
GLOBAL_PROTECT(LastAdminCalledProc)
|
||||
GLOBAL_LIST_EMPTY(AdminProcCallSpamPrevention)
|
||||
GLOBAL_PROTECT(AdminProcCallSpamPrevention)
|
||||
|
||||
/proc/WrapAdminProcCall(datum/target, procname, list/arguments)
|
||||
if(target && procname == "Del")
|
||||
to_chat(usr, "<span class='filter_adminlog'>Calling Del() is not allowed</span>")
|
||||
return
|
||||
|
||||
if(target != GLOBAL_PROC && !target.CanProcCall(procname))
|
||||
to_chat(usr, "<span class='filter_adminlog'>Proccall on [target.type]/proc/[procname] is disallowed!</span>")
|
||||
return
|
||||
var/current_caller = GLOB.AdminProcCaller
|
||||
var/ckey = usr ? usr.client.ckey : GLOB.AdminProcCaller
|
||||
if(!ckey)
|
||||
CRASH("WrapAdminProcCall with no ckey: [target] [procname] [english_list(arguments)]")
|
||||
if(current_caller && current_caller != ckey)
|
||||
if(!GLOB.AdminProcCallSpamPrevention[ckey])
|
||||
to_chat(usr, "<span class='adminnotice'>Another set of admin called procs are still running, your proc will be run after theirs finish.</span>")
|
||||
GLOB.AdminProcCallSpamPrevention[ckey] = TRUE
|
||||
UNTIL(!GLOB.AdminProcCaller)
|
||||
to_chat(usr, "<span class='adminnotice'>Running your proc</span>")
|
||||
GLOB.AdminProcCallSpamPrevention -= ckey
|
||||
else
|
||||
UNTIL(!GLOB.AdminProcCaller)
|
||||
GLOB.LastAdminCalledProc = procname
|
||||
if(target != GLOBAL_PROC)
|
||||
GLOB.LastAdminCalledTargetRef = "\ref[target]"
|
||||
GLOB.AdminProcCaller = ckey //if this runtimes, too bad for you
|
||||
++GLOB.AdminProcCallCount
|
||||
. = world.WrapAdminProcCall(target, procname, arguments)
|
||||
if(--GLOB.AdminProcCallCount == 0)
|
||||
GLOB.AdminProcCaller = null
|
||||
|
||||
//adv proc call this, ya nerds
|
||||
/world/proc/WrapAdminProcCall(datum/target, procname, list/arguments)
|
||||
if(target == GLOBAL_PROC)
|
||||
return call(procname)(arglist(arguments))
|
||||
else if(target != world)
|
||||
return call(target, procname)(arglist(arguments))
|
||||
else
|
||||
log_admin("[key_name(usr)] attempted to call world/proc/[procname] with arguments: [english_list(arguments)]")
|
||||
|
||||
/proc/IsAdminAdvancedProcCall()
|
||||
#ifdef TESTING
|
||||
return FALSE
|
||||
#else
|
||||
return usr && usr.client && GLOB.AdminProcCaller == usr.client.ckey
|
||||
#endif
|
||||
|
||||
/client/proc/callproc_datum(datum/A as null|area|mob|obj|turf)
|
||||
set category = "Debug"
|
||||
set name = "Atom ProcCall"
|
||||
set waitfor = 0
|
||||
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
|
||||
var/procname = tgui_input_text(usr, "Proc name, eg: fake_blood","Proc:", null)
|
||||
if(!procname)
|
||||
return
|
||||
if(!hascall(A,procname))
|
||||
to_chat(usr, "<span class='filter_adminlog'>" + span_red("Error: callproc_datum(): type [A.type] has no proc named [procname].") + "</span>")
|
||||
return
|
||||
var/list/lst = get_callproc_args()
|
||||
if(!lst)
|
||||
return
|
||||
|
||||
if(!A || !IsValidSrc(A))
|
||||
to_chat(usr, "<span class='warning'>Error: callproc_datum(): owner of proc no longer exists.</span>")
|
||||
return
|
||||
var/msg = "[key_name(src)] called [A]'s [procname]() with [lst.len ? "the arguments [list2params(lst)]":"no arguments"]."
|
||||
log_admin(msg)
|
||||
//message_admins(msg)
|
||||
admin_ticket_log(A, msg)
|
||||
feedback_add_details("admin_verb","TPC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
var/returnval = WrapAdminProcCall(A, procname, lst) // Pass the lst as an argument list to the proc
|
||||
. = get_callproc_returnval(returnval,procname)
|
||||
if(.)
|
||||
to_chat(usr, .)
|
||||
|
||||
/client/proc/get_callproc_args()
|
||||
var/argnum = tgui_input_number(usr, "Number of arguments","Number:",0)
|
||||
if(isnull(argnum))
|
||||
return null //Cancel
|
||||
|
||||
. = list()
|
||||
//var/list/named_args = list() //Named arguments are removed, due to them making proccalling take too long.
|
||||
while(argnum--)
|
||||
/* //Named arguments are removed, due to them making proccalling take too long.
|
||||
var/named_arg = input(usr,"Leave blank for positional argument. Positional arguments will be considered as if they were added first.", "Named argument") as text|null
|
||||
if(isnull(named_arg))
|
||||
return null //Cancel
|
||||
*/
|
||||
var/value = vv_get_value(restricted_classes = list(VV_RESTORE_DEFAULT))
|
||||
if (!value["class"])
|
||||
return null //Cancel
|
||||
/* //Named arguments are removed, due to them making proccalling take too long.
|
||||
if(named_arg)
|
||||
named_args[named_arg] = value["value"]
|
||||
else
|
||||
. += value["value"]
|
||||
if(LAZYLEN(named_args))
|
||||
. += named_args
|
||||
*/
|
||||
. += value["value"]
|
||||
|
||||
/client/proc/get_callproc_returnval(returnval,procname)
|
||||
. = ""
|
||||
if(islist(returnval))
|
||||
var/list/returnedlist = returnval
|
||||
. = "<span class='blue'>"
|
||||
if(returnedlist.len)
|
||||
var/assoc_check = returnedlist[1]
|
||||
if(istext(assoc_check) && (returnedlist[assoc_check] != null))
|
||||
. += "[procname] returned an associative list:"
|
||||
for(var/key in returnedlist)
|
||||
. += "\n[key] = [returnedlist[key]]"
|
||||
|
||||
else
|
||||
. += "[procname] returned a list:"
|
||||
for(var/elem in returnedlist)
|
||||
. += "\n[elem]"
|
||||
else
|
||||
. = "[procname] returned an empty list"
|
||||
. += "</span>"
|
||||
|
||||
else
|
||||
. = span_blue("[procname] returned: [!isnull(returnval) ? returnval : "null"]")
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
/var/create_mob_html = null
|
||||
/datum/admins/proc/create_mob(var/mob/user)
|
||||
if (!create_mob_html)
|
||||
var/mobjs = null
|
||||
mobjs = jointext(typesof(/mob), ";")
|
||||
create_mob_html = file2text('html/create_object.html')
|
||||
create_mob_html = replacetext(create_mob_html, "null /* object types */", "\"[mobjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(create_mob_html), "window=create_mob;size=680x600")
|
||||
/var/create_mob_html = null
|
||||
/datum/admins/proc/create_mob(var/mob/user)
|
||||
if (!create_mob_html)
|
||||
var/mobjs = null
|
||||
mobjs = jointext(typesof(/mob), ";")
|
||||
create_mob_html = file2text('html/create_object.html')
|
||||
create_mob_html = replacetext(create_mob_html, "null /* object types */", "\"[mobjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(create_mob_html), "window=create_mob;size=680x600")
|
||||
|
||||
@@ -1,48 +1,48 @@
|
||||
/datum/admins/proc/create_panel_helper(template)
|
||||
var/final_html = replacetext(template, "/* ref src */", "\ref[src];[HrefToken()]")
|
||||
final_html = replacetext(final_html,"/* hreftokenfield */","[HrefTokenFormField()]")
|
||||
return final_html
|
||||
|
||||
/datum/admins/proc/create_object(var/mob/user)
|
||||
var/static/create_object_html = null
|
||||
if (!create_object_html)
|
||||
var/objectjs = null
|
||||
objectjs = jointext(typesof(/obj), ";")
|
||||
create_object_html = file2text('html/create_object.html')
|
||||
create_object_html = replacetext(create_object_html, "null /* object types */", "\"[objectjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(create_object_html), "window=create_object;size=680x600")
|
||||
|
||||
|
||||
/datum/admins/proc/quick_create_object(var/mob/user)
|
||||
|
||||
var/quick_create_object_html = null
|
||||
var/pathtext = null
|
||||
var/list/choices = list("/obj",
|
||||
"/obj/structure",
|
||||
"/obj/item",
|
||||
"/obj/item/device",
|
||||
"/obj/item/weapon",
|
||||
"/obj/item/weapon/gun",
|
||||
"/obj/item/weapon/reagent_containers",
|
||||
"/obj/item/weapon/reagent_containers/food",
|
||||
"/obj/item/clothing",
|
||||
"/obj/item/weapon/storage/box/fluff", //VOREStation Edit,
|
||||
"/obj/machinery",
|
||||
"/obj/mecha",
|
||||
"/obj/item/mecha_parts",
|
||||
"/obj/item/mecha_parts/mecha_equipment")
|
||||
|
||||
pathtext = tgui_input_list(usr, "Select the path of the object you wish to create.", "Path", choices, "/obj")
|
||||
|
||||
if(!pathtext)
|
||||
return
|
||||
var path = text2path(pathtext)
|
||||
|
||||
if (!quick_create_object_html)
|
||||
var/objectjs = null
|
||||
objectjs = jointext(typesof(path), ";")
|
||||
quick_create_object_html = file2text('html/create_object.html')
|
||||
quick_create_object_html = replacetext(quick_create_object_html, "null /* object types */", "\"[objectjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(quick_create_object_html), "window=quick_create_object;size=680x600")
|
||||
/datum/admins/proc/create_panel_helper(template)
|
||||
var/final_html = replacetext(template, "/* ref src */", "\ref[src];[HrefToken()]")
|
||||
final_html = replacetext(final_html,"/* hreftokenfield */","[HrefTokenFormField()]")
|
||||
return final_html
|
||||
|
||||
/datum/admins/proc/create_object(var/mob/user)
|
||||
var/static/create_object_html = null
|
||||
if (!create_object_html)
|
||||
var/objectjs = null
|
||||
objectjs = jointext(typesof(/obj), ";")
|
||||
create_object_html = file2text('html/create_object.html')
|
||||
create_object_html = replacetext(create_object_html, "null /* object types */", "\"[objectjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(create_object_html), "window=create_object;size=680x600")
|
||||
|
||||
|
||||
/datum/admins/proc/quick_create_object(var/mob/user)
|
||||
|
||||
var/quick_create_object_html = null
|
||||
var/pathtext = null
|
||||
var/list/choices = list("/obj",
|
||||
"/obj/structure",
|
||||
"/obj/item",
|
||||
"/obj/item/device",
|
||||
"/obj/item/weapon",
|
||||
"/obj/item/weapon/gun",
|
||||
"/obj/item/weapon/reagent_containers",
|
||||
"/obj/item/weapon/reagent_containers/food",
|
||||
"/obj/item/clothing",
|
||||
"/obj/item/weapon/storage/box/fluff", //VOREStation Edit,
|
||||
"/obj/machinery",
|
||||
"/obj/mecha",
|
||||
"/obj/item/mecha_parts",
|
||||
"/obj/item/mecha_parts/mecha_equipment")
|
||||
|
||||
pathtext = tgui_input_list(usr, "Select the path of the object you wish to create.", "Path", choices, "/obj")
|
||||
|
||||
if(!pathtext)
|
||||
return
|
||||
var path = text2path(pathtext)
|
||||
|
||||
if (!quick_create_object_html)
|
||||
var/objectjs = null
|
||||
objectjs = jointext(typesof(path), ";")
|
||||
quick_create_object_html = file2text('html/create_object.html')
|
||||
quick_create_object_html = replacetext(quick_create_object_html, "null /* object types */", "\"[objectjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(quick_create_object_html), "window=quick_create_object;size=680x600")
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
/var/create_turf_html = null
|
||||
/datum/admins/proc/create_turf(var/mob/user)
|
||||
if (!create_turf_html)
|
||||
var/turfjs = null
|
||||
turfjs = jointext(typesof(/turf), ";")
|
||||
create_turf_html = file2text('html/create_object.html')
|
||||
create_turf_html = replacetext(create_turf_html, "null /* object types */", "\"[turfjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(create_turf_html), "window=create_turf;size=680x600")
|
||||
/var/create_turf_html = null
|
||||
/datum/admins/proc/create_turf(var/mob/user)
|
||||
if (!create_turf_html)
|
||||
var/turfjs = null
|
||||
turfjs = jointext(typesof(/turf), ";")
|
||||
create_turf_html = file2text('html/create_object.html')
|
||||
create_turf_html = replacetext(create_turf_html, "null /* object types */", "\"[turfjs]\"")
|
||||
|
||||
user << browse(create_panel_helper(create_turf_html), "window=create_turf;size=680x600")
|
||||
|
||||
+157
-157
@@ -1,157 +1,157 @@
|
||||
GLOBAL_VAR_INIT(href_token, GenerateToken())
|
||||
GLOBAL_PROTECT(href_token)
|
||||
|
||||
var/list/admin_datums = list()
|
||||
|
||||
/datum/admins
|
||||
var/rank = "Temporary Admin"
|
||||
var/client/owner = null
|
||||
var/rights = 0
|
||||
var/fakekey = null
|
||||
|
||||
var/datum/marked_datum
|
||||
|
||||
var/admincaster_screen = 0 //See newscaster.dm under machinery for a full description
|
||||
var/datum/feed_message/admincaster_feed_message = new /datum/feed_message //These two will act as holders.
|
||||
var/datum/feed_channel/admincaster_feed_channel = new /datum/feed_channel
|
||||
var/admincaster_signature //What you'll sign the newsfeeds as
|
||||
|
||||
var/href_token
|
||||
|
||||
|
||||
/datum/admins/New(initial_rank = "Temporary Admin", initial_rights = 0, ckey)
|
||||
if(!ckey)
|
||||
error("Admin datum created without a ckey argument. Datum has been deleted")
|
||||
qdel(src)
|
||||
return
|
||||
admincaster_signature = "[using_map.company_name] Officer #[rand(0,9)][rand(0,9)][rand(0,9)]"
|
||||
href_token = GenerateToken()
|
||||
rank = initial_rank
|
||||
rights = initial_rights
|
||||
admin_datums[ckey] = src
|
||||
if(rights & R_DEBUG) //grant profile access
|
||||
world.SetConfig("APP/admin", ckey, "role=admin")
|
||||
|
||||
/datum/admins/proc/associate(client/C)
|
||||
if(istype(C))
|
||||
owner = C
|
||||
owner.holder = src
|
||||
owner.add_admin_verbs() //TODO
|
||||
GLOB.admins |= C
|
||||
|
||||
/datum/admins/proc/disassociate()
|
||||
if(owner)
|
||||
GLOB.admins -= owner
|
||||
owner.remove_admin_verbs()
|
||||
owner.deadmin_holder = owner.holder
|
||||
owner.holder = null
|
||||
|
||||
/datum/admins/proc/reassociate()
|
||||
if(owner)
|
||||
GLOB.admins += owner
|
||||
owner.holder = src
|
||||
owner.deadmin_holder = null
|
||||
owner.add_admin_verbs()
|
||||
|
||||
/datum/admins/vv_edit_var(var_name, var_value)
|
||||
if(var_name == NAMEOF(src, rights) || var_name == NAMEOF(src, owner) || var_name == NAMEOF(src, rank))
|
||||
return FALSE
|
||||
return ..()
|
||||
|
||||
//TODO: Proccall guard, when all try/catch are removed and WrapAdminProccall is ported.
|
||||
|
||||
/*
|
||||
checks if usr is an admin with at least ONE of the flags in rights_required. (Note, they don't need all the flags)
|
||||
if rights_required == 0, then it simply checks if they are an admin.
|
||||
if it doesn't return 1 and show_msg=1 it will prints a message explaining why the check has failed
|
||||
generally it would be used like so:
|
||||
|
||||
/proc/admin_proc()
|
||||
if(!check_rights(R_ADMIN)) return
|
||||
to_world("you have enough rights!")
|
||||
|
||||
NOTE: It checks usr by default. Supply the "user" argument if you wish to check for a specific mob.
|
||||
*/
|
||||
/proc/check_rights(rights_required, show_msg=1, var/client/C = usr)
|
||||
if(ismob(C))
|
||||
var/mob/M = C
|
||||
C = M.client
|
||||
if(!C)
|
||||
return FALSE
|
||||
if(!(istype(C, /client))) // If we still didn't find a client, something is wrong.
|
||||
return FALSE
|
||||
if(!C.holder)
|
||||
if(show_msg)
|
||||
to_chat(C, "<span class='filter_adminlog warning'>Error: You are not an admin.</span>")
|
||||
return FALSE
|
||||
|
||||
if(rights_required)
|
||||
if(rights_required & C.holder.rights)
|
||||
return TRUE
|
||||
else
|
||||
if(show_msg)
|
||||
to_chat(C, "<span class='filter_adminlog warning'>Error: You do not have sufficient rights to do that. You require one of the following flags:[rights2text(rights_required," ")].</span>")
|
||||
return FALSE
|
||||
else
|
||||
return TRUE
|
||||
|
||||
//probably a bit iffy - will hopefully figure out a better solution
|
||||
/proc/check_if_greater_rights_than(client/other)
|
||||
if(usr && usr.client)
|
||||
if(usr.client.holder)
|
||||
if(!other || !other.holder)
|
||||
return 1
|
||||
if(usr.client.holder.rights != other.holder.rights)
|
||||
if( (usr.client.holder.rights & other.holder.rights) == other.holder.rights )
|
||||
return 1 //we have all the rights they have and more
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Error: Cannot proceed. They have more or equal rights to us.</span>")
|
||||
return 0
|
||||
|
||||
/client/proc/mark_datum(datum/D)
|
||||
if(!holder)
|
||||
return
|
||||
if(holder.marked_datum)
|
||||
vv_update_display(holder.marked_datum, "marked", "")
|
||||
holder.marked_datum = D
|
||||
vv_update_display(D, "marked", VV_MSG_MARKED)
|
||||
|
||||
/client/proc/mark_datum_mapview(datum/D as mob|obj|turf|area in view(view))
|
||||
set category = "Debug"
|
||||
set name = "Mark Object"
|
||||
mark_datum(D)
|
||||
|
||||
/client/proc/deadmin()
|
||||
if(holder)
|
||||
holder.disassociate()
|
||||
//qdel(holder)
|
||||
return 1
|
||||
|
||||
//This proc checks whether subject has at least ONE of the rights specified in rights_required.
|
||||
/proc/check_rights_for(client/subject, rights_required)
|
||||
if(subject && subject.holder)
|
||||
if(rights_required && !(rights_required & subject.holder.rights))
|
||||
return 0
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/proc/GenerateToken()
|
||||
. = ""
|
||||
for(var/I in 1 to 32)
|
||||
. += "[rand(10)]"
|
||||
|
||||
/proc/RawHrefToken(forceGlobal = FALSE)
|
||||
var/tok = GLOB.href_token
|
||||
if(!forceGlobal && usr)
|
||||
var/client/C = usr.client
|
||||
if(!C)
|
||||
CRASH("No client for HrefToken()!")
|
||||
var/datum/admins/holder = C.holder
|
||||
if(holder)
|
||||
tok = holder.href_token
|
||||
return tok
|
||||
|
||||
/proc/HrefToken(forceGlobal = FALSE)
|
||||
return "admin_token=[RawHrefToken(forceGlobal)]"
|
||||
|
||||
/proc/HrefTokenFormField(forceGlobal = FALSE)
|
||||
return "<input type='hidden' name='admin_token' value='[RawHrefToken(forceGlobal)]'>"
|
||||
GLOBAL_VAR_INIT(href_token, GenerateToken())
|
||||
GLOBAL_PROTECT(href_token)
|
||||
|
||||
var/list/admin_datums = list()
|
||||
|
||||
/datum/admins
|
||||
var/rank = "Temporary Admin"
|
||||
var/client/owner = null
|
||||
var/rights = 0
|
||||
var/fakekey = null
|
||||
|
||||
var/datum/marked_datum
|
||||
|
||||
var/admincaster_screen = 0 //See newscaster.dm under machinery for a full description
|
||||
var/datum/feed_message/admincaster_feed_message = new /datum/feed_message //These two will act as holders.
|
||||
var/datum/feed_channel/admincaster_feed_channel = new /datum/feed_channel
|
||||
var/admincaster_signature //What you'll sign the newsfeeds as
|
||||
|
||||
var/href_token
|
||||
|
||||
|
||||
/datum/admins/New(initial_rank = "Temporary Admin", initial_rights = 0, ckey)
|
||||
if(!ckey)
|
||||
error("Admin datum created without a ckey argument. Datum has been deleted")
|
||||
qdel(src)
|
||||
return
|
||||
admincaster_signature = "[using_map.company_name] Officer #[rand(0,9)][rand(0,9)][rand(0,9)]"
|
||||
href_token = GenerateToken()
|
||||
rank = initial_rank
|
||||
rights = initial_rights
|
||||
admin_datums[ckey] = src
|
||||
if(rights & R_DEBUG) //grant profile access
|
||||
world.SetConfig("APP/admin", ckey, "role=admin")
|
||||
|
||||
/datum/admins/proc/associate(client/C)
|
||||
if(istype(C))
|
||||
owner = C
|
||||
owner.holder = src
|
||||
owner.add_admin_verbs() //TODO
|
||||
GLOB.admins |= C
|
||||
|
||||
/datum/admins/proc/disassociate()
|
||||
if(owner)
|
||||
GLOB.admins -= owner
|
||||
owner.remove_admin_verbs()
|
||||
owner.deadmin_holder = owner.holder
|
||||
owner.holder = null
|
||||
|
||||
/datum/admins/proc/reassociate()
|
||||
if(owner)
|
||||
GLOB.admins += owner
|
||||
owner.holder = src
|
||||
owner.deadmin_holder = null
|
||||
owner.add_admin_verbs()
|
||||
|
||||
/datum/admins/vv_edit_var(var_name, var_value)
|
||||
if(var_name == NAMEOF(src, rights) || var_name == NAMEOF(src, owner) || var_name == NAMEOF(src, rank))
|
||||
return FALSE
|
||||
return ..()
|
||||
|
||||
//TODO: Proccall guard, when all try/catch are removed and WrapAdminProccall is ported.
|
||||
|
||||
/*
|
||||
checks if usr is an admin with at least ONE of the flags in rights_required. (Note, they don't need all the flags)
|
||||
if rights_required == 0, then it simply checks if they are an admin.
|
||||
if it doesn't return 1 and show_msg=1 it will prints a message explaining why the check has failed
|
||||
generally it would be used like so:
|
||||
|
||||
/proc/admin_proc()
|
||||
if(!check_rights(R_ADMIN)) return
|
||||
to_world("you have enough rights!")
|
||||
|
||||
NOTE: It checks usr by default. Supply the "user" argument if you wish to check for a specific mob.
|
||||
*/
|
||||
/proc/check_rights(rights_required, show_msg=1, var/client/C = usr)
|
||||
if(ismob(C))
|
||||
var/mob/M = C
|
||||
C = M.client
|
||||
if(!C)
|
||||
return FALSE
|
||||
if(!(istype(C, /client))) // If we still didn't find a client, something is wrong.
|
||||
return FALSE
|
||||
if(!C.holder)
|
||||
if(show_msg)
|
||||
to_chat(C, "<span class='filter_adminlog warning'>Error: You are not an admin.</span>")
|
||||
return FALSE
|
||||
|
||||
if(rights_required)
|
||||
if(rights_required & C.holder.rights)
|
||||
return TRUE
|
||||
else
|
||||
if(show_msg)
|
||||
to_chat(C, "<span class='filter_adminlog warning'>Error: You do not have sufficient rights to do that. You require one of the following flags:[rights2text(rights_required," ")].</span>")
|
||||
return FALSE
|
||||
else
|
||||
return TRUE
|
||||
|
||||
//probably a bit iffy - will hopefully figure out a better solution
|
||||
/proc/check_if_greater_rights_than(client/other)
|
||||
if(usr && usr.client)
|
||||
if(usr.client.holder)
|
||||
if(!other || !other.holder)
|
||||
return 1
|
||||
if(usr.client.holder.rights != other.holder.rights)
|
||||
if( (usr.client.holder.rights & other.holder.rights) == other.holder.rights )
|
||||
return 1 //we have all the rights they have and more
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Error: Cannot proceed. They have more or equal rights to us.</span>")
|
||||
return 0
|
||||
|
||||
/client/proc/mark_datum(datum/D)
|
||||
if(!holder)
|
||||
return
|
||||
if(holder.marked_datum)
|
||||
vv_update_display(holder.marked_datum, "marked", "")
|
||||
holder.marked_datum = D
|
||||
vv_update_display(D, "marked", VV_MSG_MARKED)
|
||||
|
||||
/client/proc/mark_datum_mapview(datum/D as mob|obj|turf|area in view(view))
|
||||
set category = "Debug"
|
||||
set name = "Mark Object"
|
||||
mark_datum(D)
|
||||
|
||||
/client/proc/deadmin()
|
||||
if(holder)
|
||||
holder.disassociate()
|
||||
//qdel(holder)
|
||||
return 1
|
||||
|
||||
//This proc checks whether subject has at least ONE of the rights specified in rights_required.
|
||||
/proc/check_rights_for(client/subject, rights_required)
|
||||
if(subject && subject.holder)
|
||||
if(rights_required && !(rights_required & subject.holder.rights))
|
||||
return 0
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/proc/GenerateToken()
|
||||
. = ""
|
||||
for(var/I in 1 to 32)
|
||||
. += "[rand(10)]"
|
||||
|
||||
/proc/RawHrefToken(forceGlobal = FALSE)
|
||||
var/tok = GLOB.href_token
|
||||
if(!forceGlobal && usr)
|
||||
var/client/C = usr.client
|
||||
if(!C)
|
||||
CRASH("No client for HrefToken()!")
|
||||
var/datum/admins/holder = C.holder
|
||||
if(holder)
|
||||
tok = holder.href_token
|
||||
return tok
|
||||
|
||||
/proc/HrefToken(forceGlobal = FALSE)
|
||||
return "admin_token=[RawHrefToken(forceGlobal)]"
|
||||
|
||||
/proc/HrefTokenFormField(forceGlobal = FALSE)
|
||||
return "<input type='hidden' name='admin_token' value='[RawHrefToken(forceGlobal)]'>"
|
||||
|
||||
+274
-274
@@ -1,274 +1,274 @@
|
||||
var/savefile/Banlistjob
|
||||
|
||||
|
||||
/proc/_jobban_isbanned(var/client/clientvar, var/rank)
|
||||
if(!clientvar) return 1
|
||||
ClearTempbansjob()
|
||||
var/id = clientvar.computer_id
|
||||
var/key = clientvar.ckey
|
||||
if (guest_jobbans(rank))
|
||||
if(config.guest_jobban && IsGuestKey(key))
|
||||
return 1
|
||||
Banlistjob.cd = "/base"
|
||||
if (Banlistjob.dir.Find("[key][id][rank]"))
|
||||
return 1
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
if ((id == Banlistjob["id"] || key == Banlistjob["key"]) && rank == Banlistjob["rank"])
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/proc/LoadBansjob()
|
||||
|
||||
Banlistjob = new("data/job_fullnew.bdb")
|
||||
log_admin("Loading Banlistjob")
|
||||
|
||||
if (!length(Banlistjob.dir)) log_admin("Banlistjob is empty.")
|
||||
|
||||
if (!Banlistjob.dir.Find("base"))
|
||||
log_admin("Banlistjob missing base dir.")
|
||||
Banlistjob.dir.Add("base")
|
||||
Banlistjob.cd = "/base"
|
||||
else if (Banlistjob.dir.Find("base"))
|
||||
Banlistjob.cd = "/base"
|
||||
|
||||
ClearTempbansjob()
|
||||
return 1
|
||||
|
||||
/proc/ClearTempbansjob()
|
||||
UpdateTime()
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
//if (!Banlistjob["key"] || !Banlistjob["id"])
|
||||
// RemoveBanjob(A, "full")
|
||||
// log_admin("Invalid Ban.")
|
||||
// message_admins("Invalid Ban.")
|
||||
// continue
|
||||
|
||||
if (!Banlistjob["temp"]) continue
|
||||
if (CMinutes >= Banlistjob["minutes"]) RemoveBanjob(A)
|
||||
|
||||
return 1
|
||||
|
||||
|
||||
/proc/AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, rank)
|
||||
UpdateTime()
|
||||
var/bantimestamp
|
||||
if (temp)
|
||||
UpdateTime()
|
||||
bantimestamp = CMinutes + minutes
|
||||
if(rank == "Heads")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Personnel")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Site Manager")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
return 1
|
||||
if(rank == "Security")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Warden")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Detective")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Security Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
return 1
|
||||
if(rank == "Engineering")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Atmospheric Technician")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
return 1
|
||||
if(rank == "Research")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Scientist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
return 1
|
||||
if(rank == "Medical")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Medical Doctor")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chemist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
return 1
|
||||
if(rank == "CE_Station_Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
return 1
|
||||
if(rank == "CE_Atmospheric_Tech")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Atmospheric Technician")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
return 1
|
||||
if(rank == "CE_Shaft_Miner")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Shaft Miner")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
return 1
|
||||
if(rank == "Chemist_RD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chemist")
|
||||
return 1
|
||||
if(rank == "Geneticist_RD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist")
|
||||
return 1
|
||||
if(rank == "MD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Medical Doctor")
|
||||
return 1
|
||||
if(rank == "Scientist_RD")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Scientist")
|
||||
return 1
|
||||
if(rank == "AI_Cyborg")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "AI")
|
||||
return 1
|
||||
if(rank == "Detective_HoS")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Detective")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security")
|
||||
return 1
|
||||
if(rank == "Virologist_RD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Virologist")
|
||||
return 1
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
if ( Banlistjob.dir.Find("[ckey][computerid][rank]") )
|
||||
to_chat(usr, span_red("Banjob already exists."))
|
||||
return 0
|
||||
else
|
||||
Banlistjob.dir.Add("[ckey][computerid][rank]")
|
||||
Banlistjob.cd = "/base/[ckey][computerid][rank]"
|
||||
Banlistjob["key"] << ckey
|
||||
Banlistjob["id"] << computerid
|
||||
Banlistjob["rank"] << rank
|
||||
Banlistjob["reason"] << reason
|
||||
Banlistjob["bannedby"] << bannedby
|
||||
Banlistjob["temp"] << temp
|
||||
if (temp)
|
||||
Banlistjob["minutes"] << bantimestamp
|
||||
admin_action_message(bannedby, ckey, "jobbanned-"+rank, reason, temp ? minutes : -1) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/RemoveBanjob(foldername)
|
||||
var/key
|
||||
var/id
|
||||
var/rank
|
||||
Banlistjob.cd = "/base/[foldername]"
|
||||
Banlistjob["key"] >> key
|
||||
Banlistjob["id"] >> id
|
||||
Banlistjob["rank"] >> rank
|
||||
Banlistjob.cd = "/base"
|
||||
|
||||
if (!Banlistjob.dir.Remove(foldername)) return 0
|
||||
|
||||
if(!usr)
|
||||
log_admin("Banjob Expired: [key]")
|
||||
message_admins("Banjob Expired: [key]")
|
||||
else
|
||||
log_admin("[key_name_admin(usr)] unjobbanned [key] from [rank]")
|
||||
message_admins("[key_name_admin(usr)] unjobbanned:[key] from [rank]")
|
||||
ban_unban_log_save("[key_name_admin(usr)] unjobbanned [key] from [rank]")
|
||||
feedback_inc("ban_job_unban",1)
|
||||
feedback_add_details("ban_job_unban","- [rank]")
|
||||
|
||||
for (var/A in Banlistjob.dir)
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
if ((key == Banlistjob["key"] || id == Banlistjob["id"]) && (rank == Banlistjob["rank"]))
|
||||
Banlistjob.cd = "/base"
|
||||
Banlistjob.dir.Remove(A)
|
||||
continue
|
||||
admin_action_message(usr.key, key, "unjobbanned-"+rank, "\[Unban\]", 0) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/GetBanExpjob(minutes as num)
|
||||
UpdateTime()
|
||||
var/exp = minutes - CMinutes
|
||||
if (exp <= 0)
|
||||
return 0
|
||||
else
|
||||
var/timeleftstring
|
||||
if (exp >= 1440) //1440 = 1 day in minutes
|
||||
timeleftstring = "[round(exp / 1440, 0.1)] Days"
|
||||
else if (exp >= 60) //60 = 1 hour in minutes
|
||||
timeleftstring = "[round(exp / 60, 0.1)] Hours"
|
||||
else
|
||||
timeleftstring = "[exp] Minutes"
|
||||
return timeleftstring
|
||||
|
||||
/datum/admins/proc/unjobbanpanel()
|
||||
var/count = 0
|
||||
var/dat
|
||||
//var/dat = "<HR><B>Unban Player:</B> <font color='blue'>(U) = Unban , (E) = Edit Ban</font> <font color='green'>(Total<HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 </font>>"
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
count++
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
dat += text("<tr><td><A href='?src=\ref[src];[HrefToken()];unjobbanf=[Banlistjob["key"]][Banlistjob["id"]][Banlistjob["rank"]]'>(U)</A> Key: <B>[Banlistjob["key"]] </B>Rank: <B>[Banlistjob["rank"]]</B></td><td> ([Banlistjob["temp"] ? "[GetBanExpjob(Banlistjob["minutes"]) ? GetBanExpjob(Banlistjob["minutes"]) : "Removal pending" ]" : "Permaban"])</td><td>(By: [Banlistjob["bannedby"]])</td><td>(Reason: [Banlistjob["reason"]])</td></tr>")
|
||||
|
||||
dat += "</table>"
|
||||
dat = "<HR><B>Bans:</B> <FONT COLOR=blue>(U) = Unban , </FONT> - <FONT COLOR=green>([count] Bans)</FONT><HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 >[dat]"
|
||||
usr << browse(dat, "window=unbanp;size=875x400")
|
||||
|
||||
/*/datum/admins/proc/permjobban(ckey, computerid, reason, bannedby, temp, minutes, rank)
|
||||
if(AddBanjob(ckey, computerid, reason, usr.ckey, 0, 0, job))
|
||||
to_chat(M, "<font color='red'><BIG><B>You have been banned from [job] by [usr.client.ckey].\nReason: [reason].</B></BIG></font>")
|
||||
to_chat(M, "<font color='red'>This is a permanent ban.</font>")
|
||||
if(config.banappeals)
|
||||
to_chat(M, "<font color='red'>To try to resolve this matter head to [config.banappeals]</font>")
|
||||
else
|
||||
to_chat(M, "<font color='red'>No ban appeals URL has been set.</font>")
|
||||
log_admin("[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis is a permanent ban.")
|
||||
message_admins("<font color='blue'>[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis is a permanent ban.</font>")
|
||||
/datum/admins/proc/timejobban(ckey, computerid, reason, bannedby, temp, minutes, rank)
|
||||
if(AddBanjob(ckey, computerid, reason, usr.ckey, 1, mins, job))
|
||||
to_chat(M, "<font color='red'><BIG><B>You have been jobbanned from [job] by [usr.client.ckey].\nReason: [reason].</B></BIG></font>")
|
||||
to_chat(M, "<font color='red'>This is a temporary ban, it will be removed in [mins] minutes.</font>")
|
||||
if(config.banappeals)
|
||||
to_chat(M, "<font color='red'>To try to resolve this matter head to [config.banappeals]</font>")
|
||||
else
|
||||
to_chat(M, "<font color='red'>No ban appeals URL has been set.</font>")
|
||||
log_admin("[usr.client.ckey] has jobbanned from [job] [ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.")
|
||||
message_admins("<font color='blue'>[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.</font>")*/
|
||||
//////////////////////////////////// DEBUG ////////////////////////////////////
|
||||
|
||||
/proc/CreateBansjob()
|
||||
|
||||
UpdateTime()
|
||||
|
||||
var/i
|
||||
var/last
|
||||
|
||||
for(i=0, i<1001, i++)
|
||||
var/a = pick(1,0)
|
||||
var/b = pick(1,0)
|
||||
if(b)
|
||||
Banlistjob.cd = "/base"
|
||||
Banlistjob.dir.Add("trash[i]trashid[i]")
|
||||
Banlistjob.cd = "/base/trash[i]trashid[i]"
|
||||
to_chat(Banlistjob["key"], "trash[i]")
|
||||
else
|
||||
Banlistjob.cd = "/base"
|
||||
Banlistjob.dir.Add("[last]trashid[i]")
|
||||
Banlistjob.cd = "/base/[last]trashid[i]"
|
||||
Banlistjob["key"] << last
|
||||
to_chat(Banlistjob["id"], "trashid[i]")
|
||||
to_chat(Banlistjob["reason"], "Trashban[i].")
|
||||
Banlistjob["temp"] << a
|
||||
Banlistjob["minutes"] << CMinutes + rand(1,2000)
|
||||
to_chat(Banlistjob["bannedby"], "trashmin")
|
||||
last = "trash[i]"
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
|
||||
/proc/ClearAllBansjob()
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
RemoveBanjob(A, "full")
|
||||
var/savefile/Banlistjob
|
||||
|
||||
|
||||
/proc/_jobban_isbanned(var/client/clientvar, var/rank)
|
||||
if(!clientvar) return 1
|
||||
ClearTempbansjob()
|
||||
var/id = clientvar.computer_id
|
||||
var/key = clientvar.ckey
|
||||
if (guest_jobbans(rank))
|
||||
if(config.guest_jobban && IsGuestKey(key))
|
||||
return 1
|
||||
Banlistjob.cd = "/base"
|
||||
if (Banlistjob.dir.Find("[key][id][rank]"))
|
||||
return 1
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
if ((id == Banlistjob["id"] || key == Banlistjob["key"]) && rank == Banlistjob["rank"])
|
||||
return 1
|
||||
return 0
|
||||
|
||||
/proc/LoadBansjob()
|
||||
|
||||
Banlistjob = new("data/job_fullnew.bdb")
|
||||
log_admin("Loading Banlistjob")
|
||||
|
||||
if (!length(Banlistjob.dir)) log_admin("Banlistjob is empty.")
|
||||
|
||||
if (!Banlistjob.dir.Find("base"))
|
||||
log_admin("Banlistjob missing base dir.")
|
||||
Banlistjob.dir.Add("base")
|
||||
Banlistjob.cd = "/base"
|
||||
else if (Banlistjob.dir.Find("base"))
|
||||
Banlistjob.cd = "/base"
|
||||
|
||||
ClearTempbansjob()
|
||||
return 1
|
||||
|
||||
/proc/ClearTempbansjob()
|
||||
UpdateTime()
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
//if (!Banlistjob["key"] || !Banlistjob["id"])
|
||||
// RemoveBanjob(A, "full")
|
||||
// log_admin("Invalid Ban.")
|
||||
// message_admins("Invalid Ban.")
|
||||
// continue
|
||||
|
||||
if (!Banlistjob["temp"]) continue
|
||||
if (CMinutes >= Banlistjob["minutes"]) RemoveBanjob(A)
|
||||
|
||||
return 1
|
||||
|
||||
|
||||
/proc/AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, rank)
|
||||
UpdateTime()
|
||||
var/bantimestamp
|
||||
if (temp)
|
||||
UpdateTime()
|
||||
bantimestamp = CMinutes + minutes
|
||||
if(rank == "Heads")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Personnel")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Site Manager")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
return 1
|
||||
if(rank == "Security")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Warden")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Detective")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Security Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
return 1
|
||||
if(rank == "Engineering")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Atmospheric Technician")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
return 1
|
||||
if(rank == "Research")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Scientist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
return 1
|
||||
if(rank == "Medical")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Medical Doctor")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chemist")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
return 1
|
||||
if(rank == "CE_Station_Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Engineer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
return 1
|
||||
if(rank == "CE_Atmospheric_Tech")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Atmospheric Technician")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
return 1
|
||||
if(rank == "CE_Shaft_Miner")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Shaft Miner")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer")
|
||||
return 1
|
||||
if(rank == "Chemist_RD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chemist")
|
||||
return 1
|
||||
if(rank == "Geneticist_RD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist")
|
||||
return 1
|
||||
if(rank == "MD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Medical Doctor")
|
||||
return 1
|
||||
if(rank == "Scientist_RD")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Scientist")
|
||||
return 1
|
||||
if(rank == "AI_Cyborg")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "AI")
|
||||
return 1
|
||||
if(rank == "Detective_HoS")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Detective")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security")
|
||||
return 1
|
||||
if(rank == "Virologist_RD_CMO")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director")
|
||||
AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Virologist")
|
||||
return 1
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
if ( Banlistjob.dir.Find("[ckey][computerid][rank]") )
|
||||
to_chat(usr, span_red("Banjob already exists."))
|
||||
return 0
|
||||
else
|
||||
Banlistjob.dir.Add("[ckey][computerid][rank]")
|
||||
Banlistjob.cd = "/base/[ckey][computerid][rank]"
|
||||
Banlistjob["key"] << ckey
|
||||
Banlistjob["id"] << computerid
|
||||
Banlistjob["rank"] << rank
|
||||
Banlistjob["reason"] << reason
|
||||
Banlistjob["bannedby"] << bannedby
|
||||
Banlistjob["temp"] << temp
|
||||
if (temp)
|
||||
Banlistjob["minutes"] << bantimestamp
|
||||
admin_action_message(bannedby, ckey, "jobbanned-"+rank, reason, temp ? minutes : -1) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/RemoveBanjob(foldername)
|
||||
var/key
|
||||
var/id
|
||||
var/rank
|
||||
Banlistjob.cd = "/base/[foldername]"
|
||||
Banlistjob["key"] >> key
|
||||
Banlistjob["id"] >> id
|
||||
Banlistjob["rank"] >> rank
|
||||
Banlistjob.cd = "/base"
|
||||
|
||||
if (!Banlistjob.dir.Remove(foldername)) return 0
|
||||
|
||||
if(!usr)
|
||||
log_admin("Banjob Expired: [key]")
|
||||
message_admins("Banjob Expired: [key]")
|
||||
else
|
||||
log_admin("[key_name_admin(usr)] unjobbanned [key] from [rank]")
|
||||
message_admins("[key_name_admin(usr)] unjobbanned:[key] from [rank]")
|
||||
ban_unban_log_save("[key_name_admin(usr)] unjobbanned [key] from [rank]")
|
||||
feedback_inc("ban_job_unban",1)
|
||||
feedback_add_details("ban_job_unban","- [rank]")
|
||||
|
||||
for (var/A in Banlistjob.dir)
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
if ((key == Banlistjob["key"] || id == Banlistjob["id"]) && (rank == Banlistjob["rank"]))
|
||||
Banlistjob.cd = "/base"
|
||||
Banlistjob.dir.Remove(A)
|
||||
continue
|
||||
admin_action_message(usr.key, key, "unjobbanned-"+rank, "\[Unban\]", 0) //VOREStation Add
|
||||
return 1
|
||||
|
||||
/proc/GetBanExpjob(minutes as num)
|
||||
UpdateTime()
|
||||
var/exp = minutes - CMinutes
|
||||
if (exp <= 0)
|
||||
return 0
|
||||
else
|
||||
var/timeleftstring
|
||||
if (exp >= 1440) //1440 = 1 day in minutes
|
||||
timeleftstring = "[round(exp / 1440, 0.1)] Days"
|
||||
else if (exp >= 60) //60 = 1 hour in minutes
|
||||
timeleftstring = "[round(exp / 60, 0.1)] Hours"
|
||||
else
|
||||
timeleftstring = "[exp] Minutes"
|
||||
return timeleftstring
|
||||
|
||||
/datum/admins/proc/unjobbanpanel()
|
||||
var/count = 0
|
||||
var/dat
|
||||
//var/dat = "<HR><B>Unban Player:</B> <font color='blue'>(U) = Unban , (E) = Edit Ban</font> <font color='green'>(Total<HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 </font>>"
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
count++
|
||||
Banlistjob.cd = "/base/[A]"
|
||||
dat += text("<tr><td><A href='?src=\ref[src];[HrefToken()];unjobbanf=[Banlistjob["key"]][Banlistjob["id"]][Banlistjob["rank"]]'>(U)</A> Key: <B>[Banlistjob["key"]] </B>Rank: <B>[Banlistjob["rank"]]</B></td><td> ([Banlistjob["temp"] ? "[GetBanExpjob(Banlistjob["minutes"]) ? GetBanExpjob(Banlistjob["minutes"]) : "Removal pending" ]" : "Permaban"])</td><td>(By: [Banlistjob["bannedby"]])</td><td>(Reason: [Banlistjob["reason"]])</td></tr>")
|
||||
|
||||
dat += "</table>"
|
||||
dat = "<HR><B>Bans:</B> <FONT COLOR=blue>(U) = Unban , </FONT> - <FONT COLOR=green>([count] Bans)</FONT><HR><table border=1 rules=all frame=void cellspacing=0 cellpadding=3 >[dat]"
|
||||
usr << browse(dat, "window=unbanp;size=875x400")
|
||||
|
||||
/*/datum/admins/proc/permjobban(ckey, computerid, reason, bannedby, temp, minutes, rank)
|
||||
if(AddBanjob(ckey, computerid, reason, usr.ckey, 0, 0, job))
|
||||
to_chat(M, "<font color='red'><BIG><B>You have been banned from [job] by [usr.client.ckey].\nReason: [reason].</B></BIG></font>")
|
||||
to_chat(M, "<font color='red'>This is a permanent ban.</font>")
|
||||
if(config.banappeals)
|
||||
to_chat(M, "<font color='red'>To try to resolve this matter head to [config.banappeals]</font>")
|
||||
else
|
||||
to_chat(M, "<font color='red'>No ban appeals URL has been set.</font>")
|
||||
log_admin("[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis is a permanent ban.")
|
||||
message_admins("<font color='blue'>[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis is a permanent ban.</font>")
|
||||
/datum/admins/proc/timejobban(ckey, computerid, reason, bannedby, temp, minutes, rank)
|
||||
if(AddBanjob(ckey, computerid, reason, usr.ckey, 1, mins, job))
|
||||
to_chat(M, "<font color='red'><BIG><B>You have been jobbanned from [job] by [usr.client.ckey].\nReason: [reason].</B></BIG></font>")
|
||||
to_chat(M, "<font color='red'>This is a temporary ban, it will be removed in [mins] minutes.</font>")
|
||||
if(config.banappeals)
|
||||
to_chat(M, "<font color='red'>To try to resolve this matter head to [config.banappeals]</font>")
|
||||
else
|
||||
to_chat(M, "<font color='red'>No ban appeals URL has been set.</font>")
|
||||
log_admin("[usr.client.ckey] has jobbanned from [job] [ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.")
|
||||
message_admins("<font color='blue'>[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.</font>")*/
|
||||
//////////////////////////////////// DEBUG ////////////////////////////////////
|
||||
|
||||
/proc/CreateBansjob()
|
||||
|
||||
UpdateTime()
|
||||
|
||||
var/i
|
||||
var/last
|
||||
|
||||
for(i=0, i<1001, i++)
|
||||
var/a = pick(1,0)
|
||||
var/b = pick(1,0)
|
||||
if(b)
|
||||
Banlistjob.cd = "/base"
|
||||
Banlistjob.dir.Add("trash[i]trashid[i]")
|
||||
Banlistjob.cd = "/base/trash[i]trashid[i]"
|
||||
to_chat(Banlistjob["key"], "trash[i]")
|
||||
else
|
||||
Banlistjob.cd = "/base"
|
||||
Banlistjob.dir.Add("[last]trashid[i]")
|
||||
Banlistjob.cd = "/base/[last]trashid[i]"
|
||||
Banlistjob["key"] << last
|
||||
to_chat(Banlistjob["id"], "trashid[i]")
|
||||
to_chat(Banlistjob["reason"], "Trashban[i].")
|
||||
Banlistjob["temp"] << a
|
||||
Banlistjob["minutes"] << CMinutes + rand(1,2000)
|
||||
to_chat(Banlistjob["bannedby"], "trashmin")
|
||||
last = "trash[i]"
|
||||
|
||||
Banlistjob.cd = "/base"
|
||||
|
||||
/proc/ClearAllBansjob()
|
||||
Banlistjob.cd = "/base"
|
||||
for (var/A in Banlistjob.dir)
|
||||
RemoveBanjob(A, "full")
|
||||
|
||||
@@ -1,149 +1,149 @@
|
||||
/client/proc/edit_admin_permissions()
|
||||
set category = "Admin"
|
||||
set name = "Permissions Panel"
|
||||
set desc = "Edit admin permissions"
|
||||
if(!check_rights(R_PERMISSIONS)) return
|
||||
usr.client.holder.edit_admin_permissions()
|
||||
|
||||
/datum/admins/proc/edit_admin_permissions()
|
||||
if(!check_rights(R_PERMISSIONS)) return
|
||||
|
||||
var/output = {"<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<title>Permissions Panel</title>
|
||||
<script type='text/javascript' src='search.js'></script>
|
||||
<link rel='stylesheet' type='text/css' href='panels.css'>
|
||||
</head>
|
||||
<body onload='selectTextField();updateSearch();'>
|
||||
<div id='main'><table id='searchable' cellspacing='0'>
|
||||
<tr class='title'>
|
||||
<th style='width:125px;text-align:right;'>CKEY <a class='small' href='?src=\ref[src];[HrefToken()];editrights=add'>\[+\]</a></th>
|
||||
<th style='width:125px;'>RANK</th><th style='width:100%;'>PERMISSIONS</th>
|
||||
</tr>
|
||||
"}
|
||||
|
||||
for(var/adm_ckey in admin_datums)
|
||||
var/datum/admins/D = admin_datums[adm_ckey]
|
||||
if(!D) continue
|
||||
var/rank = D.rank ? D.rank : "*none*"
|
||||
var/rights = rights2text(D.rights," ")
|
||||
if(!rights) rights = "*none*"
|
||||
|
||||
output += "<tr>"
|
||||
output += "<td style='text-align:right;'>[adm_ckey] <a class='small' href='?src=\ref[src];[HrefToken()];editrights=remove;ckey=[adm_ckey]'>\[-\]</a></td>"
|
||||
output += "<td><a href='?src=\ref[src];[HrefToken()];editrights=rank;ckey=[adm_ckey]'>[rank]</a></td>"
|
||||
output += "<td><a class='small' href='?src=\ref[src];[HrefToken()];editrights=permissions;ckey=[adm_ckey]'>[rights]</a></td>"
|
||||
output += "</tr>"
|
||||
|
||||
output += {"
|
||||
</table></div>
|
||||
<div id='top'><b>Search:</b> <input type='text' id='filter' value='' style='width:70%;' onkeyup='updateSearch();'></div>
|
||||
</body>
|
||||
</html>"}
|
||||
|
||||
usr << browse(output,"window=editrights;size=600x500")
|
||||
|
||||
/datum/admins/proc/log_admin_rank_modification(var/adm_ckey, var/new_rank)
|
||||
if(config.admin_legacy_system) return
|
||||
|
||||
if(!usr.client)
|
||||
return
|
||||
|
||||
if(!usr.client.holder || !(usr.client.holder.rights & R_PERMISSIONS))
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("You do not have permission to do this!")]</span>")
|
||||
return
|
||||
|
||||
establish_db_connection()
|
||||
|
||||
if(!dbcon.IsConnected())
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Failed to establish database connection")]</span>")
|
||||
return
|
||||
|
||||
if(!adm_ckey || !new_rank)
|
||||
return
|
||||
|
||||
adm_ckey = ckey(adm_ckey)
|
||||
|
||||
if(!adm_ckey)
|
||||
return
|
||||
|
||||
if(!istext(adm_ckey) || !istext(new_rank))
|
||||
return
|
||||
|
||||
var/DBQuery/select_query = dbcon.NewQuery("SELECT id FROM erro_admin WHERE ckey = '[adm_ckey]'")
|
||||
select_query.Execute()
|
||||
|
||||
var/new_admin = 1
|
||||
var/admin_id
|
||||
while(select_query.NextRow())
|
||||
new_admin = 0
|
||||
admin_id = text2num(select_query.item[1])
|
||||
|
||||
if(new_admin)
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("INSERT INTO `erro_admin` (`id`, `ckey`, `rank`, `level`, `flags`) VALUES (null, '[adm_ckey]', '[new_rank]', -1, 0)")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Added new admin [adm_ckey] to rank [new_rank]');")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("New admin added.")]</span>")
|
||||
else
|
||||
if(!isnull(admin_id) && isnum(admin_id))
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("UPDATE `erro_admin` SET rank = '[new_rank]' WHERE id = [admin_id]")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Edited the rank of [adm_ckey] to [new_rank]');")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Admin rank changed.")]</span>")
|
||||
|
||||
/datum/admins/proc/log_admin_permission_modification(var/adm_ckey, var/new_permission)
|
||||
if(config.admin_legacy_system) return
|
||||
|
||||
if(!usr.client)
|
||||
return
|
||||
|
||||
if(!usr.client.holder || !(usr.client.holder.rights & R_PERMISSIONS))
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red(">You do not have permission to do this!")]</span>")
|
||||
return
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Failed to establish database connection!")]</span>")
|
||||
return
|
||||
|
||||
if(!adm_ckey || !new_permission)
|
||||
return
|
||||
|
||||
adm_ckey = ckey(adm_ckey)
|
||||
|
||||
if(!adm_ckey)
|
||||
return
|
||||
|
||||
if(istext(new_permission))
|
||||
new_permission = text2num(new_permission)
|
||||
|
||||
if(!istext(adm_ckey) || !isnum(new_permission))
|
||||
return
|
||||
|
||||
var/DBQuery/select_query = dbcon.NewQuery("SELECT id, flags FROM erro_admin WHERE ckey = '[adm_ckey]'")
|
||||
select_query.Execute()
|
||||
|
||||
var/admin_id
|
||||
var/admin_rights
|
||||
while(select_query.NextRow())
|
||||
admin_id = text2num(select_query.item[1])
|
||||
admin_rights = text2num(select_query.item[2])
|
||||
|
||||
if(!admin_id)
|
||||
return
|
||||
|
||||
if(admin_rights & new_permission) //This admin already has this permission, so we are removing it.
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("UPDATE `erro_admin` SET flags = [admin_rights & ~new_permission] WHERE id = [admin_id]")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Removed permission [rights2text(new_permission)] (flag = [new_permission]) to admin [adm_ckey]');")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Permission removed.")]</span>")
|
||||
else //This admin doesn't have this permission, so we are adding it.
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("UPDATE `erro_admin` SET flags = '[admin_rights | new_permission]' WHERE id = [admin_id]")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Added permission [rights2text(new_permission)] (flag = [new_permission]) to admin [adm_ckey]')")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Permission added.")]</span>")
|
||||
/client/proc/edit_admin_permissions()
|
||||
set category = "Admin"
|
||||
set name = "Permissions Panel"
|
||||
set desc = "Edit admin permissions"
|
||||
if(!check_rights(R_PERMISSIONS)) return
|
||||
usr.client.holder.edit_admin_permissions()
|
||||
|
||||
/datum/admins/proc/edit_admin_permissions()
|
||||
if(!check_rights(R_PERMISSIONS)) return
|
||||
|
||||
var/output = {"<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<title>Permissions Panel</title>
|
||||
<script type='text/javascript' src='search.js'></script>
|
||||
<link rel='stylesheet' type='text/css' href='panels.css'>
|
||||
</head>
|
||||
<body onload='selectTextField();updateSearch();'>
|
||||
<div id='main'><table id='searchable' cellspacing='0'>
|
||||
<tr class='title'>
|
||||
<th style='width:125px;text-align:right;'>CKEY <a class='small' href='?src=\ref[src];[HrefToken()];editrights=add'>\[+\]</a></th>
|
||||
<th style='width:125px;'>RANK</th><th style='width:100%;'>PERMISSIONS</th>
|
||||
</tr>
|
||||
"}
|
||||
|
||||
for(var/adm_ckey in admin_datums)
|
||||
var/datum/admins/D = admin_datums[adm_ckey]
|
||||
if(!D) continue
|
||||
var/rank = D.rank ? D.rank : "*none*"
|
||||
var/rights = rights2text(D.rights," ")
|
||||
if(!rights) rights = "*none*"
|
||||
|
||||
output += "<tr>"
|
||||
output += "<td style='text-align:right;'>[adm_ckey] <a class='small' href='?src=\ref[src];[HrefToken()];editrights=remove;ckey=[adm_ckey]'>\[-\]</a></td>"
|
||||
output += "<td><a href='?src=\ref[src];[HrefToken()];editrights=rank;ckey=[adm_ckey]'>[rank]</a></td>"
|
||||
output += "<td><a class='small' href='?src=\ref[src];[HrefToken()];editrights=permissions;ckey=[adm_ckey]'>[rights]</a></td>"
|
||||
output += "</tr>"
|
||||
|
||||
output += {"
|
||||
</table></div>
|
||||
<div id='top'><b>Search:</b> <input type='text' id='filter' value='' style='width:70%;' onkeyup='updateSearch();'></div>
|
||||
</body>
|
||||
</html>"}
|
||||
|
||||
usr << browse(output,"window=editrights;size=600x500")
|
||||
|
||||
/datum/admins/proc/log_admin_rank_modification(var/adm_ckey, var/new_rank)
|
||||
if(config.admin_legacy_system) return
|
||||
|
||||
if(!usr.client)
|
||||
return
|
||||
|
||||
if(!usr.client.holder || !(usr.client.holder.rights & R_PERMISSIONS))
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("You do not have permission to do this!")]</span>")
|
||||
return
|
||||
|
||||
establish_db_connection()
|
||||
|
||||
if(!dbcon.IsConnected())
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Failed to establish database connection")]</span>")
|
||||
return
|
||||
|
||||
if(!adm_ckey || !new_rank)
|
||||
return
|
||||
|
||||
adm_ckey = ckey(adm_ckey)
|
||||
|
||||
if(!adm_ckey)
|
||||
return
|
||||
|
||||
if(!istext(adm_ckey) || !istext(new_rank))
|
||||
return
|
||||
|
||||
var/DBQuery/select_query = dbcon.NewQuery("SELECT id FROM erro_admin WHERE ckey = '[adm_ckey]'")
|
||||
select_query.Execute()
|
||||
|
||||
var/new_admin = 1
|
||||
var/admin_id
|
||||
while(select_query.NextRow())
|
||||
new_admin = 0
|
||||
admin_id = text2num(select_query.item[1])
|
||||
|
||||
if(new_admin)
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("INSERT INTO `erro_admin` (`id`, `ckey`, `rank`, `level`, `flags`) VALUES (null, '[adm_ckey]', '[new_rank]', -1, 0)")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Added new admin [adm_ckey] to rank [new_rank]');")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("New admin added.")]</span>")
|
||||
else
|
||||
if(!isnull(admin_id) && isnum(admin_id))
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("UPDATE `erro_admin` SET rank = '[new_rank]' WHERE id = [admin_id]")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Edited the rank of [adm_ckey] to [new_rank]');")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Admin rank changed.")]</span>")
|
||||
|
||||
/datum/admins/proc/log_admin_permission_modification(var/adm_ckey, var/new_permission)
|
||||
if(config.admin_legacy_system) return
|
||||
|
||||
if(!usr.client)
|
||||
return
|
||||
|
||||
if(!usr.client.holder || !(usr.client.holder.rights & R_PERMISSIONS))
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red(">You do not have permission to do this!")]</span>")
|
||||
return
|
||||
|
||||
establish_db_connection()
|
||||
if(!dbcon.IsConnected())
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_red("Failed to establish database connection!")]</span>")
|
||||
return
|
||||
|
||||
if(!adm_ckey || !new_permission)
|
||||
return
|
||||
|
||||
adm_ckey = ckey(adm_ckey)
|
||||
|
||||
if(!adm_ckey)
|
||||
return
|
||||
|
||||
if(istext(new_permission))
|
||||
new_permission = text2num(new_permission)
|
||||
|
||||
if(!istext(adm_ckey) || !isnum(new_permission))
|
||||
return
|
||||
|
||||
var/DBQuery/select_query = dbcon.NewQuery("SELECT id, flags FROM erro_admin WHERE ckey = '[adm_ckey]'")
|
||||
select_query.Execute()
|
||||
|
||||
var/admin_id
|
||||
var/admin_rights
|
||||
while(select_query.NextRow())
|
||||
admin_id = text2num(select_query.item[1])
|
||||
admin_rights = text2num(select_query.item[2])
|
||||
|
||||
if(!admin_id)
|
||||
return
|
||||
|
||||
if(admin_rights & new_permission) //This admin already has this permission, so we are removing it.
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("UPDATE `erro_admin` SET flags = [admin_rights & ~new_permission] WHERE id = [admin_id]")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Removed permission [rights2text(new_permission)] (flag = [new_permission]) to admin [adm_ckey]');")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Permission removed.")]</span>")
|
||||
else //This admin doesn't have this permission, so we are adding it.
|
||||
var/DBQuery/insert_query = dbcon.NewQuery("UPDATE `erro_admin` SET flags = '[admin_rights | new_permission]' WHERE id = [admin_id]")
|
||||
insert_query.Execute()
|
||||
var/DBQuery/log_query = dbcon.NewQuery("INSERT INTO `test`.`erro_admin_log` (`id` ,`datetime` ,`adminckey` ,`adminip` ,`log` ) VALUES (NULL , NOW( ) , '[usr.ckey]', '[usr.client.address]', 'Added permission [rights2text(new_permission)] (flag = [new_permission]) to admin [adm_ckey]')")
|
||||
log_query.Execute()
|
||||
to_chat(usr, "<span class='filter_adminlog'>[span_blue("Permission added.")]</span>")
|
||||
|
||||
@@ -1,44 +1,44 @@
|
||||
/datum/admin_secret_item/admin_secret/admin_logs
|
||||
name = "Admin Logs"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/admin_logs/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Admin Log<HR></B>"
|
||||
for(var/l in admin_log)
|
||||
dat += "<li>[l]</li>"
|
||||
if(!admin_log.len)
|
||||
dat += "No-one has done anything this round!"
|
||||
|
||||
var/datum/browser/popup = new(user, "adminlogs", "[src]", 550, 650, src)
|
||||
popup.set_content(jointext(dat,null))
|
||||
popup.open()
|
||||
|
||||
onclose(user, "adminlogs")
|
||||
|
||||
|
||||
/datum/admin_secret_item/admin_secret/round_logs
|
||||
name = "Round Dialogue Logs"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/round_logs/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Dialogue Log<HR></B>"
|
||||
|
||||
dat += "<fieldset style='border: 2px solid white; display: inline'>"
|
||||
|
||||
for(var/l in GLOB.round_text_log)
|
||||
dat += "<li>[l]</li>"
|
||||
|
||||
dat += "</fieldset>"
|
||||
|
||||
if(!GLOB.round_text_log)
|
||||
dat += "No-one has said anything this round! (How odd?)"
|
||||
|
||||
var/datum/browser/popup = new(user, "dialoguelogs", "[src]", 550, 650, src)
|
||||
popup.set_content(jointext(dat,null))
|
||||
popup.open()
|
||||
|
||||
onclose(user, "dialoguelogs")
|
||||
/datum/admin_secret_item/admin_secret/admin_logs
|
||||
name = "Admin Logs"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/admin_logs/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Admin Log<HR></B>"
|
||||
for(var/l in admin_log)
|
||||
dat += "<li>[l]</li>"
|
||||
if(!admin_log.len)
|
||||
dat += "No-one has done anything this round!"
|
||||
|
||||
var/datum/browser/popup = new(user, "adminlogs", "[src]", 550, 650, src)
|
||||
popup.set_content(jointext(dat,null))
|
||||
popup.open()
|
||||
|
||||
onclose(user, "adminlogs")
|
||||
|
||||
|
||||
/datum/admin_secret_item/admin_secret/round_logs
|
||||
name = "Round Dialogue Logs"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/round_logs/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Dialogue Log<HR></B>"
|
||||
|
||||
dat += "<fieldset style='border: 2px solid white; display: inline'>"
|
||||
|
||||
for(var/l in GLOB.round_text_log)
|
||||
dat += "<li>[l]</li>"
|
||||
|
||||
dat += "</fieldset>"
|
||||
|
||||
if(!GLOB.round_text_log)
|
||||
dat += "No-one has said anything this round! (How odd?)"
|
||||
|
||||
var/datum/browser/popup = new(user, "dialoguelogs", "[src]", 550, 650, src)
|
||||
popup.set_content(jointext(dat,null))
|
||||
popup.open()
|
||||
|
||||
onclose(user, "dialoguelogs")
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
/datum/admin_secret_item/admin_secret/alter_narise
|
||||
name = "Alter Nar-Sie"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/alter_narise/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/choice = tgui_alert(user, "How do you wish for Nar-Sie to interact with its surroundings?","NarChoice",list("CultStation13", "Nar-Singulo"))
|
||||
if(choice == "CultStation13")
|
||||
log_and_message_admins("has set narsie's behaviour to \"CultStation13\".", user)
|
||||
narsie_behaviour = choice
|
||||
if(choice == "Nar-Singulo")
|
||||
log_and_message_admins("has set narsie's behaviour to \"Nar-Singulo\".", user)
|
||||
narsie_behaviour = choice
|
||||
/datum/admin_secret_item/admin_secret/alter_narise
|
||||
name = "Alter Nar-Sie"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/alter_narise/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/choice = tgui_alert(user, "How do you wish for Nar-Sie to interact with its surroundings?","NarChoice",list("CultStation13", "Nar-Singulo"))
|
||||
if(choice == "CultStation13")
|
||||
log_and_message_admins("has set narsie's behaviour to \"CultStation13\".", user)
|
||||
narsie_behaviour = choice
|
||||
if(choice == "Nar-Singulo")
|
||||
log_and_message_admins("has set narsie's behaviour to \"Nar-Singulo\".", user)
|
||||
narsie_behaviour = choice
|
||||
|
||||
@@ -1,12 +1,12 @@
|
||||
/datum/admin_secret_item/admin_secret/bombing_list
|
||||
name = "Bombing List"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/bombing_list/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/dat = "<B>Bombing List</B>"
|
||||
for(var/l in bombers)
|
||||
dat += text("[l]<BR>")
|
||||
user << browse(dat, "window=bombers")
|
||||
/datum/admin_secret_item/admin_secret/bombing_list
|
||||
name = "Bombing List"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/bombing_list/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/dat = "<B>Bombing List</B>"
|
||||
for(var/l in bombers)
|
||||
dat += text("[l]<BR>")
|
||||
user << browse(dat, "window=bombers")
|
||||
|
||||
@@ -1,37 +1,37 @@
|
||||
/datum/admin_secret_item/admin_secret/jump_shuttle
|
||||
name = "Jump a Shuttle"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/jump_shuttle/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/jump_shuttle/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle do you want to jump?", "Shuttle Choice", SSshuttles.shuttles)
|
||||
if (!shuttle_tag) return
|
||||
|
||||
var/datum/shuttle/S = SSshuttles.shuttles[shuttle_tag]
|
||||
|
||||
var/list/area_choices = return_areas()
|
||||
var/origin_area = tgui_input_list(user, "Which area is the shuttle at now? (MAKE SURE THIS IS CORRECT OR THINGS WILL BREAK)", "Area Choice", area_choices)
|
||||
if (!origin_area) return
|
||||
|
||||
var/destination_area = tgui_input_list(user, "Which area is the shuttle at now? (MAKE SURE THIS IS CORRECT OR THINGS WILL BREAK)", "Area Choice", area_choices)
|
||||
if (!destination_area) return
|
||||
|
||||
var/long_jump = tgui_alert(user, "Is there a transition area for this jump?","Transition?", list("Yes","No"))
|
||||
if (long_jump == "Yes")
|
||||
var/transition_area = tgui_input_list(user, "Which area is the transition area? (MAKE SURE THIS IS CORRECT OR THINGS WILL BREAK)", "Area Choice", area_choices)
|
||||
if (!transition_area) return
|
||||
|
||||
var/move_duration = tgui_input_number(user, "How many seconds will this jump take?")
|
||||
|
||||
S.long_jump(area_choices[origin_area], area_choices[destination_area], area_choices[transition_area], move_duration)
|
||||
message_admins("<span class='notice'>[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] lasting [move_duration] seconds for the [shuttle_tag] shuttle</span>", 1)
|
||||
log_admin("[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] lasting [move_duration] seconds for the [shuttle_tag] shuttle")
|
||||
else
|
||||
S.short_jump(area_choices[origin_area], area_choices[destination_area])
|
||||
message_admins("<span class='notice'>[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] for the [shuttle_tag] shuttle</span>", 1)
|
||||
log_admin("[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] for the [shuttle_tag] shuttle")
|
||||
/datum/admin_secret_item/admin_secret/jump_shuttle
|
||||
name = "Jump a Shuttle"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/jump_shuttle/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/jump_shuttle/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle do you want to jump?", "Shuttle Choice", SSshuttles.shuttles)
|
||||
if (!shuttle_tag) return
|
||||
|
||||
var/datum/shuttle/S = SSshuttles.shuttles[shuttle_tag]
|
||||
|
||||
var/list/area_choices = return_areas()
|
||||
var/origin_area = tgui_input_list(user, "Which area is the shuttle at now? (MAKE SURE THIS IS CORRECT OR THINGS WILL BREAK)", "Area Choice", area_choices)
|
||||
if (!origin_area) return
|
||||
|
||||
var/destination_area = tgui_input_list(user, "Which area is the shuttle at now? (MAKE SURE THIS IS CORRECT OR THINGS WILL BREAK)", "Area Choice", area_choices)
|
||||
if (!destination_area) return
|
||||
|
||||
var/long_jump = tgui_alert(user, "Is there a transition area for this jump?","Transition?", list("Yes","No"))
|
||||
if (long_jump == "Yes")
|
||||
var/transition_area = tgui_input_list(user, "Which area is the transition area? (MAKE SURE THIS IS CORRECT OR THINGS WILL BREAK)", "Area Choice", area_choices)
|
||||
if (!transition_area) return
|
||||
|
||||
var/move_duration = tgui_input_number(user, "How many seconds will this jump take?")
|
||||
|
||||
S.long_jump(area_choices[origin_area], area_choices[destination_area], area_choices[transition_area], move_duration)
|
||||
message_admins("<span class='notice'>[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] lasting [move_duration] seconds for the [shuttle_tag] shuttle</span>", 1)
|
||||
log_admin("[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] lasting [move_duration] seconds for the [shuttle_tag] shuttle")
|
||||
else
|
||||
S.short_jump(area_choices[origin_area], area_choices[destination_area])
|
||||
message_admins("<span class='notice'>[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] for the [shuttle_tag] shuttle</span>", 1)
|
||||
log_admin("[key_name_admin(user)] has initiated a jump from [origin_area] to [destination_area] for the [shuttle_tag] shuttle")
|
||||
|
||||
@@ -1,26 +1,26 @@
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle
|
||||
name = "Launch a Shuttle"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/list/valid_shuttles = list()
|
||||
for (var/shuttle_tag in SSshuttles.shuttles)
|
||||
if (istype(SSshuttles.shuttles[shuttle_tag], /datum/shuttle/autodock))
|
||||
valid_shuttles += shuttle_tag
|
||||
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle do you want to launch?", "Shuttle Choice", valid_shuttles)
|
||||
if (!shuttle_tag)
|
||||
return
|
||||
|
||||
var/datum/shuttle/autodock/S = SSshuttles.shuttles[shuttle_tag]
|
||||
if (S.can_launch())
|
||||
S.launch(user)
|
||||
log_and_message_admins("launched the [shuttle_tag] shuttle", user)
|
||||
else
|
||||
tgui_alert_async(user, "The [shuttle_tag] shuttle cannot be launched at this time. It's probably busy.")
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle
|
||||
name = "Launch a Shuttle"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/list/valid_shuttles = list()
|
||||
for (var/shuttle_tag in SSshuttles.shuttles)
|
||||
if (istype(SSshuttles.shuttles[shuttle_tag], /datum/shuttle/autodock))
|
||||
valid_shuttles += shuttle_tag
|
||||
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle do you want to launch?", "Shuttle Choice", valid_shuttles)
|
||||
if (!shuttle_tag)
|
||||
return
|
||||
|
||||
var/datum/shuttle/autodock/S = SSshuttles.shuttles[shuttle_tag]
|
||||
if (S.can_launch())
|
||||
S.launch(user)
|
||||
log_and_message_admins("launched the [shuttle_tag] shuttle", user)
|
||||
else
|
||||
tgui_alert_async(user, "The [shuttle_tag] shuttle cannot be launched at this time. It's probably busy.")
|
||||
|
||||
@@ -1,26 +1,26 @@
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle_forced
|
||||
name = "Launch a Shuttle (Forced)"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle_forced/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle_forced/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/list/valid_shuttles = list()
|
||||
for (var/shuttle_tag in SSshuttles.shuttles)
|
||||
if (istype(SSshuttles.shuttles[shuttle_tag], /datum/shuttle/autodock))
|
||||
valid_shuttles += shuttle_tag
|
||||
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle's launch do you want to force?", "Shuttle Choice", valid_shuttles)
|
||||
if (!shuttle_tag)
|
||||
return
|
||||
|
||||
var/datum/shuttle/autodock/S = SSshuttles.shuttles[shuttle_tag]
|
||||
if (S.can_force())
|
||||
S.force_launch(user)
|
||||
log_and_message_admins("forced the [shuttle_tag] shuttle", user)
|
||||
else
|
||||
tgui_alert_async(user, "The [shuttle_tag] shuttle launch cannot be forced at this time. It's busy, or hasn't been launched yet.")
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle_forced
|
||||
name = "Launch a Shuttle (Forced)"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle_forced/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/launch_shuttle_forced/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/list/valid_shuttles = list()
|
||||
for (var/shuttle_tag in SSshuttles.shuttles)
|
||||
if (istype(SSshuttles.shuttles[shuttle_tag], /datum/shuttle/autodock))
|
||||
valid_shuttles += shuttle_tag
|
||||
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle's launch do you want to force?", "Shuttle Choice", valid_shuttles)
|
||||
if (!shuttle_tag)
|
||||
return
|
||||
|
||||
var/datum/shuttle/autodock/S = SSshuttles.shuttles[shuttle_tag]
|
||||
if (S.can_force())
|
||||
S.force_launch(user)
|
||||
log_and_message_admins("forced the [shuttle_tag] shuttle", user)
|
||||
else
|
||||
tgui_alert_async(user, "The [shuttle_tag] shuttle launch cannot be forced at this time. It's busy, or hasn't been launched yet.")
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
/datum/admin_secret_item/admin_secret/list_dna
|
||||
name = "List DNA (Blood)"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/list_dna/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Showing DNA from blood.</B><HR>"
|
||||
dat += "<table cellspacing=5><tr><th>Name</th><th>DNA</th><th>Blood Type</th></tr>"
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
if(H.dna && H.ckey)
|
||||
dat += "<tr><td>[H]</td><td>[H.dna.unique_enzymes]</td><td>[H.b_type]</td></tr>"
|
||||
dat += "</table>"
|
||||
user << browse(dat, "window=DNA;size=440x410")
|
||||
/datum/admin_secret_item/admin_secret/list_dna
|
||||
name = "List DNA (Blood)"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/list_dna/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Showing DNA from blood.</B><HR>"
|
||||
dat += "<table cellspacing=5><tr><th>Name</th><th>DNA</th><th>Blood Type</th></tr>"
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
if(H.dna && H.ckey)
|
||||
dat += "<tr><td>[H]</td><td>[H.dna.unique_enzymes]</td><td>[H.b_type]</td></tr>"
|
||||
dat += "</table>"
|
||||
user << browse(dat, "window=DNA;size=440x410")
|
||||
|
||||
@@ -1,19 +1,19 @@
|
||||
/datum/admin_secret_item/admin_secret/list_fingerprints
|
||||
name = "List Fingerprints"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/list_fingerprints/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Showing Fingerprints.</B><HR>"
|
||||
dat += "<table cellspacing=5><tr><th>Name</th><th>Fingerprints</th></tr>"
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
if(H.ckey)
|
||||
if(H.dna && H.dna.uni_identity)
|
||||
dat += "<tr><td>[H]</td><td>[md5(H.dna.uni_identity)]</td></tr>"
|
||||
else if(H.dna && !H.dna.uni_identity)
|
||||
dat += "<tr><td>[H]</td><td>H.dna.uni_identity = null</td></tr>"
|
||||
else if(!H.dna)
|
||||
dat += "<tr><td>[H]</td><td>H.dna = null</td></tr>"
|
||||
dat += "</table>"
|
||||
user << browse(dat, "window=fingerprints;size=440x410")
|
||||
/datum/admin_secret_item/admin_secret/list_fingerprints
|
||||
name = "List Fingerprints"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/list_fingerprints/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat = "<B>Showing Fingerprints.</B><HR>"
|
||||
dat += "<table cellspacing=5><tr><th>Name</th><th>Fingerprints</th></tr>"
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
if(H.ckey)
|
||||
if(H.dna && H.dna.uni_identity)
|
||||
dat += "<tr><td>[H]</td><td>[md5(H.dna.uni_identity)]</td></tr>"
|
||||
else if(H.dna && !H.dna.uni_identity)
|
||||
dat += "<tr><td>[H]</td><td>H.dna.uni_identity = null</td></tr>"
|
||||
else if(!H.dna)
|
||||
dat += "<tr><td>[H]</td><td>H.dna = null</td></tr>"
|
||||
dat += "</table>"
|
||||
user << browse(dat, "window=fingerprints;size=440x410")
|
||||
|
||||
@@ -1,27 +1,27 @@
|
||||
/datum/admin_secret_item/admin_secret/move_shuttle
|
||||
name = "Move a Shuttle"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/move_shuttle/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/move_shuttle/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/confirm = tgui_alert(user, "This command directly moves a shuttle from one area to another. DO NOT USE THIS UNLESS YOU ARE DEBUGGING A SHUTTLE AND YOU KNOW WHAT YOU ARE DOING.", "Are you sure?", list("Ok", "Cancel"))
|
||||
if (confirm == "Cancel")
|
||||
return
|
||||
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle do you want to jump?", "Shuttle Choice", SSshuttles.shuttles)
|
||||
if (!shuttle_tag) return
|
||||
|
||||
var/datum/shuttle/S = SSshuttles.shuttles[shuttle_tag]
|
||||
|
||||
var/destination_tag = tgui_input_list(user, "Which landmark do you want to jump to? (IF YOU GET THIS WRONG THINGS WILL BREAK)", "Landmark Choice", SSshuttles.registered_shuttle_landmarks)
|
||||
if (!destination_tag) return
|
||||
var/destination_location = SSshuttles.get_landmark(destination_tag)
|
||||
if (!destination_location) return
|
||||
|
||||
S.attempt_move(destination_location)
|
||||
log_and_message_admins("moved the [shuttle_tag] shuttle", user)
|
||||
/datum/admin_secret_item/admin_secret/move_shuttle
|
||||
name = "Move a Shuttle"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/move_shuttle/can_execute(var/mob/user)
|
||||
if(!SSshuttles) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/move_shuttle/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/confirm = tgui_alert(user, "This command directly moves a shuttle from one area to another. DO NOT USE THIS UNLESS YOU ARE DEBUGGING A SHUTTLE AND YOU KNOW WHAT YOU ARE DOING.", "Are you sure?", list("Ok", "Cancel"))
|
||||
if (confirm == "Cancel")
|
||||
return
|
||||
|
||||
var/shuttle_tag = tgui_input_list(user, "Which shuttle do you want to jump?", "Shuttle Choice", SSshuttles.shuttles)
|
||||
if (!shuttle_tag) return
|
||||
|
||||
var/datum/shuttle/S = SSshuttles.shuttles[shuttle_tag]
|
||||
|
||||
var/destination_tag = tgui_input_list(user, "Which landmark do you want to jump to? (IF YOU GET THIS WRONG THINGS WILL BREAK)", "Landmark Choice", SSshuttles.registered_shuttle_landmarks)
|
||||
if (!destination_tag) return
|
||||
var/destination_location = SSshuttles.get_landmark(destination_tag)
|
||||
if (!destination_location) return
|
||||
|
||||
S.attempt_move(destination_location)
|
||||
log_and_message_admins("moved the [shuttle_tag] shuttle", user)
|
||||
|
||||
@@ -1,38 +1,38 @@
|
||||
/datum/admin_secret_item/admin_secret/prison_warp
|
||||
name = "Prison Warp"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/prison_warp/can_execute(var/mob/user)
|
||||
if(!ticker) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/prison_warp/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
var/turf/T = get_turf(H)
|
||||
var/security = 0
|
||||
if((T in using_map.admin_levels) || prisonwarped.Find(H))
|
||||
//don't warp them if they aren't ready or are already there
|
||||
continue
|
||||
H.Paralyse(5)
|
||||
if(H.wear_id)
|
||||
var/obj/item/weapon/card/id/id = H.get_idcard()
|
||||
for(var/A in id.access)
|
||||
if(A == access_security)
|
||||
security++
|
||||
if(!security)
|
||||
//strip their stuff before they teleport into a cell :downs:
|
||||
for(var/obj/item/weapon/W in H)
|
||||
if(istype(W, /obj/item/organ/external))
|
||||
continue
|
||||
//don't strip organs
|
||||
H.drop_from_inventory(W)
|
||||
//teleport person to cell
|
||||
H.loc = pick(prisonwarp)
|
||||
H.equip_to_slot_or_del(new /obj/item/clothing/under/color/prison(H), slot_w_uniform)
|
||||
H.equip_to_slot_or_del(new /obj/item/clothing/shoes/orange(H), slot_shoes)
|
||||
else
|
||||
//teleport security person
|
||||
H.loc = pick(prisonsecuritywarp)
|
||||
prisonwarped += H
|
||||
/datum/admin_secret_item/admin_secret/prison_warp
|
||||
name = "Prison Warp"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/prison_warp/can_execute(var/mob/user)
|
||||
if(!ticker) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/prison_warp/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
var/turf/T = get_turf(H)
|
||||
var/security = 0
|
||||
if((T in using_map.admin_levels) || prisonwarped.Find(H))
|
||||
//don't warp them if they aren't ready or are already there
|
||||
continue
|
||||
H.Paralyse(5)
|
||||
if(H.wear_id)
|
||||
var/obj/item/weapon/card/id/id = H.get_idcard()
|
||||
for(var/A in id.access)
|
||||
if(A == access_security)
|
||||
security++
|
||||
if(!security)
|
||||
//strip their stuff before they teleport into a cell :downs:
|
||||
for(var/obj/item/weapon/W in H)
|
||||
if(istype(W, /obj/item/organ/external))
|
||||
continue
|
||||
//don't strip organs
|
||||
H.drop_from_inventory(W)
|
||||
//teleport person to cell
|
||||
H.loc = pick(prisonwarp)
|
||||
H.equip_to_slot_or_del(new /obj/item/clothing/under/color/prison(H), slot_w_uniform)
|
||||
H.equip_to_slot_or_del(new /obj/item/clothing/shoes/orange(H), slot_shoes)
|
||||
else
|
||||
//teleport security person
|
||||
H.loc = pick(prisonsecuritywarp)
|
||||
prisonwarped += H
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/admin_secret/show_ai_laws
|
||||
name = "Show AI laws"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_ai_laws/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
user.client.holder.output_ai_laws()
|
||||
/datum/admin_secret_item/admin_secret/show_ai_laws
|
||||
name = "Show AI laws"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_ai_laws/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
user.client.holder.output_ai_laws()
|
||||
|
||||
@@ -1,12 +1,12 @@
|
||||
/datum/admin_secret_item/admin_secret/show_crew_manifest
|
||||
name = "Show Crew Manifest"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_crew_manifest/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat
|
||||
dat += "<h4>Crew Manifest</h4>"
|
||||
dat += data_core.get_manifest()
|
||||
|
||||
user << browse(dat, "window=manifest;size=370x420;can_close=1")
|
||||
/datum/admin_secret_item/admin_secret/show_crew_manifest
|
||||
name = "Show Crew Manifest"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_crew_manifest/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/dat
|
||||
dat += "<h4>Crew Manifest</h4>"
|
||||
dat += data_core.get_manifest()
|
||||
|
||||
user << browse(dat, "window=manifest;size=370x420;can_close=1")
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
/datum/admin_secret_item/admin_secret/show_game_mode
|
||||
name = "Show Game Mode"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_game_mode/can_execute(var/mob/user)
|
||||
if(!ticker)
|
||||
return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_game_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
if (ticker.mode) tgui_alert_async(usr, "The game mode is [ticker.mode.name]")
|
||||
else tgui_alert_async(usr, "For some reason there's a ticker, but not a game mode")
|
||||
/datum/admin_secret_item/admin_secret/show_game_mode
|
||||
name = "Show Game Mode"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_game_mode/can_execute(var/mob/user)
|
||||
if(!ticker)
|
||||
return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_game_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
if (ticker.mode) tgui_alert_async(usr, "The game mode is [ticker.mode.name]")
|
||||
else tgui_alert_async(usr, "For some reason there's a ticker, but not a game mode")
|
||||
|
||||
@@ -1,15 +1,15 @@
|
||||
/datum/admin_secret_item/admin_secret/show_law_changes
|
||||
name = "Show law changes"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_law_changes/name()
|
||||
return "Show Last [length(lawchanges)] Law change\s"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_law_changes/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/dat = "<B>Showing last [length(lawchanges)] law changes.</B><HR>"
|
||||
for(var/sig in lawchanges)
|
||||
dat += "[sig]<BR>"
|
||||
user << browse(dat, "window=lawchanges;size=800x500")
|
||||
/datum/admin_secret_item/admin_secret/show_law_changes
|
||||
name = "Show law changes"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_law_changes/name()
|
||||
return "Show Last [length(lawchanges)] Law change\s"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_law_changes/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/dat = "<B>Showing last [length(lawchanges)] law changes.</B><HR>"
|
||||
for(var/sig in lawchanges)
|
||||
dat += "[sig]<BR>"
|
||||
user << browse(dat, "window=lawchanges;size=800x500")
|
||||
|
||||
@@ -1,15 +1,15 @@
|
||||
/datum/admin_secret_item/admin_secret/show_signalers
|
||||
name = "Show Last Signalers"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_signalers/name()
|
||||
return "Show Last [length(lastsignalers)] Signaler\s"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_signalers/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/dat = "<B>Showing last [length(lastsignalers)] signalers.</B><HR>"
|
||||
for(var/sig in lastsignalers)
|
||||
dat += "[sig]<BR>"
|
||||
user << browse(dat, "window=lastsignalers;size=800x500")
|
||||
/datum/admin_secret_item/admin_secret/show_signalers
|
||||
name = "Show Last Signalers"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_signalers/name()
|
||||
return "Show Last [length(lastsignalers)] Signaler\s"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/show_signalers/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/dat = "<B>Showing last [length(lastsignalers)] signalers.</B><HR>"
|
||||
for(var/sig in lastsignalers)
|
||||
dat += "[sig]<BR>"
|
||||
user << browse(dat, "window=lastsignalers;size=800x500")
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/admin_secret/traitors_and_objectives
|
||||
name = "Show current traitors and objectives"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/traitors_and_objectives/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
user.client.holder.check_antagonists()
|
||||
/datum/admin_secret_item/admin_secret/traitors_and_objectives
|
||||
name = "Show current traitors and objectives"
|
||||
|
||||
/datum/admin_secret_item/admin_secret/traitors_and_objectives/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
user.client.holder.check_antagonists()
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
/datum/admin_secret_item/final_solution/summon_narsie
|
||||
name = "Summon Nar-Sie"
|
||||
|
||||
/datum/admin_secret_item/final_solution/summon_narsie/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/choice = tgui_alert(user, "You sure you want to end the round and summon Nar-Sie at your location? Misuse of this could result in removal of flags or hilarity.","WARNING!",list("PRAISE SATAN", "Cancel"))
|
||||
if(choice == "PRAISE SATAN")
|
||||
new /obj/singularity/narsie/large(get_turf(user))
|
||||
log_and_message_admins("has summoned Nar-Sie and brought about a new realm of suffering.", user)
|
||||
/datum/admin_secret_item/final_solution/summon_narsie
|
||||
name = "Summon Nar-Sie"
|
||||
|
||||
/datum/admin_secret_item/final_solution/summon_narsie/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/choice = tgui_alert(user, "You sure you want to end the round and summon Nar-Sie at your location? Misuse of this could result in removal of flags or hilarity.","WARNING!",list("PRAISE SATAN", "Cancel"))
|
||||
if(choice == "PRAISE SATAN")
|
||||
new /obj/singularity/narsie/large(get_turf(user))
|
||||
log_and_message_admins("has summoned Nar-Sie and brought about a new realm of suffering.", user)
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
/datum/admin_secret_item/final_solution/supermatter_cascade
|
||||
name = "Supermatter Cascade"
|
||||
|
||||
/datum/admin_secret_item/final_solution/supermatter_cascade/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/choice = tgui_alert(user, "You sure you want to destroy the universe and create a large explosion at your location? Misuse of this could result in removal of flags or hilarity.","WARNING!", list("NO TIME TO EXPLAIN", "Cancel"))
|
||||
if(choice == "NO TIME TO EXPLAIN")
|
||||
explosion(get_turf(user), 8, 16, 24, 32, 1)
|
||||
new /turf/unsimulated/wall/supermatter(get_turf(user))
|
||||
SetUniversalState(/datum/universal_state/supermatter_cascade)
|
||||
message_admins("[key_name_admin(user)] has managed to destroy the universe with a supermatter cascade. Good job, [key_name_admin(user)]")
|
||||
/datum/admin_secret_item/final_solution/supermatter_cascade
|
||||
name = "Supermatter Cascade"
|
||||
|
||||
/datum/admin_secret_item/final_solution/supermatter_cascade/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
var/choice = tgui_alert(user, "You sure you want to destroy the universe and create a large explosion at your location? Misuse of this could result in removal of flags or hilarity.","WARNING!", list("NO TIME TO EXPLAIN", "Cancel"))
|
||||
if(choice == "NO TIME TO EXPLAIN")
|
||||
explosion(get_turf(user), 8, 16, 24, 32, 1)
|
||||
new /turf/unsimulated/wall/supermatter(get_turf(user))
|
||||
SetUniversalState(/datum/universal_state/supermatter_cascade)
|
||||
message_admins("[key_name_admin(user)] has managed to destroy the universe with a supermatter cascade. Good job, [key_name_admin(user)]")
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/fun_secret/break_all_lights
|
||||
name = "Break All Lights"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/break_all_lights/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
lightsout(0,0)
|
||||
/datum/admin_secret_item/fun_secret/break_all_lights
|
||||
name = "Break All Lights"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/break_all_lights/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
lightsout(0,0)
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/fun_secret/break_some_lights
|
||||
name = "Break Some Lights"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/break_some_lights/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
lightsout(1,2)
|
||||
/datum/admin_secret_item/fun_secret/break_some_lights
|
||||
name = "Break Some Lights"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/break_some_lights/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
lightsout(1,2)
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
/datum/admin_secret_item/fun_secret/fix_all_lights
|
||||
name = "Fix All Lights"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/fix_all_lights/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/obj/machinery/light/L in machines)
|
||||
L.fix()
|
||||
/datum/admin_secret_item/fun_secret/fix_all_lights
|
||||
name = "Fix All Lights"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/fix_all_lights/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/obj/machinery/light/L in machines)
|
||||
L.fix()
|
||||
|
||||
@@ -1,48 +1,48 @@
|
||||
/datum/admin_secret_item/fun_secret/ghost_mode
|
||||
name = "Ghost Mode"
|
||||
var/list/affected_mobs
|
||||
|
||||
/datum/admin_secret_item/fun_secret/ghost_mode/New()
|
||||
..()
|
||||
affected_mobs = list()
|
||||
|
||||
/datum/admin_secret_item/fun_secret/ghost_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/list/affected_areas = list()
|
||||
for(var/mob/M in living_mob_list)
|
||||
if(M.stat == CONSCIOUS && !(M in affected_mobs))
|
||||
affected_mobs |= M
|
||||
switch(rand(1,4))
|
||||
if(1)
|
||||
M.show_message(text("<span class='notice'>You shudder as if cold...</span>"), 1)
|
||||
if(2)
|
||||
M.show_message(text("<span class='notice'>You feel something gliding across your back...</span>"), 1)
|
||||
if(3)
|
||||
M.show_message(text("<span class='notice'>Your eyes twitch, you feel like something you can't see is here...</span>"), 1)
|
||||
if(4)
|
||||
M.show_message(text("<span class='notice'>You notice something moving out of the corner of your eye, but nothing is there...</span>"), 1)
|
||||
|
||||
for(var/obj/W in orange(5,M))
|
||||
if(prob(25) && !W.anchored)
|
||||
step_rand(W)
|
||||
|
||||
var/area/A = get_area(M)
|
||||
if(A.requires_power && !A.always_unpowered && A.power_light && (A.z in using_map.player_levels))
|
||||
affected_areas |= get_area(M)
|
||||
|
||||
affected_mobs |= user
|
||||
for(var/area/AffectedArea in affected_areas)
|
||||
AffectedArea.power_light = 0
|
||||
AffectedArea.power_change()
|
||||
spawn(rand(25,50))
|
||||
AffectedArea.power_light = 1
|
||||
AffectedArea.power_change()
|
||||
|
||||
sleep(100)
|
||||
for(var/mob/M in affected_mobs)
|
||||
M.show_message(text("<span class='notice'>The chilling wind suddenly stops...</span>"), 1)
|
||||
affected_mobs.Cut()
|
||||
affected_areas.Cut()
|
||||
/datum/admin_secret_item/fun_secret/ghost_mode
|
||||
name = "Ghost Mode"
|
||||
var/list/affected_mobs
|
||||
|
||||
/datum/admin_secret_item/fun_secret/ghost_mode/New()
|
||||
..()
|
||||
affected_mobs = list()
|
||||
|
||||
/datum/admin_secret_item/fun_secret/ghost_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
var/list/affected_areas = list()
|
||||
for(var/mob/M in living_mob_list)
|
||||
if(M.stat == CONSCIOUS && !(M in affected_mobs))
|
||||
affected_mobs |= M
|
||||
switch(rand(1,4))
|
||||
if(1)
|
||||
M.show_message(text("<span class='notice'>You shudder as if cold...</span>"), 1)
|
||||
if(2)
|
||||
M.show_message(text("<span class='notice'>You feel something gliding across your back...</span>"), 1)
|
||||
if(3)
|
||||
M.show_message(text("<span class='notice'>Your eyes twitch, you feel like something you can't see is here...</span>"), 1)
|
||||
if(4)
|
||||
M.show_message(text("<span class='notice'>You notice something moving out of the corner of your eye, but nothing is there...</span>"), 1)
|
||||
|
||||
for(var/obj/W in orange(5,M))
|
||||
if(prob(25) && !W.anchored)
|
||||
step_rand(W)
|
||||
|
||||
var/area/A = get_area(M)
|
||||
if(A.requires_power && !A.always_unpowered && A.power_light && (A.z in using_map.player_levels))
|
||||
affected_areas |= get_area(M)
|
||||
|
||||
affected_mobs |= user
|
||||
for(var/area/AffectedArea in affected_areas)
|
||||
AffectedArea.power_light = 0
|
||||
AffectedArea.power_change()
|
||||
spawn(rand(25,50))
|
||||
AffectedArea.power_light = 1
|
||||
AffectedArea.power_change()
|
||||
|
||||
sleep(100)
|
||||
for(var/mob/M in affected_mobs)
|
||||
M.show_message(text("<span class='notice'>The chilling wind suddenly stops...</span>"), 1)
|
||||
affected_mobs.Cut()
|
||||
affected_areas.Cut()
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/fun_secret/only_one
|
||||
name = "There Can Be Only One"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/only_one/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
only_one()
|
||||
/datum/admin_secret_item/fun_secret/only_one
|
||||
name = "There Can Be Only One"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/only_one/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
only_one()
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
/datum/admin_secret_item/fun_secret/paintbal_mode
|
||||
name = "Paintball Mode"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/paintbal_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/species in GLOB.all_species)
|
||||
var/datum/species/S = GLOB.all_species[species]
|
||||
S.blood_color = "rainbow"
|
||||
for(var/obj/effect/decal/cleanable/blood/B in world)
|
||||
B.basecolor = "rainbow"
|
||||
B.update_icon()
|
||||
/datum/admin_secret_item/fun_secret/paintbal_mode
|
||||
name = "Paintball Mode"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/paintbal_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/species in GLOB.all_species)
|
||||
var/datum/species/S = GLOB.all_species[species]
|
||||
S.blood_color = "rainbow"
|
||||
for(var/obj/effect/decal/cleanable/blood/B in world)
|
||||
B.basecolor = "rainbow"
|
||||
B.update_icon()
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/fun_secret/power_all_smes
|
||||
name = "Power All SMES"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/power_all_smes/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
power_restore_quick()
|
||||
/datum/admin_secret_item/fun_secret/power_all_smes
|
||||
name = "Power All SMES"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/power_all_smes/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
power_restore_quick()
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
/datum/admin_secret_item/fun_secret/remove_all_clothing
|
||||
name = "Remove ALL Clothing"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/remove_all_clothing/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/obj/item/clothing/O in world)
|
||||
qdel(O)
|
||||
/datum/admin_secret_item/fun_secret/remove_all_clothing
|
||||
name = "Remove ALL Clothing"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/remove_all_clothing/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/obj/item/clothing/O in world)
|
||||
qdel(O)
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
/datum/admin_secret_item/fun_secret/remove_internal_clothing
|
||||
name = "Remove 'Internal' Clothing"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/remove_internal_clothing/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/obj/item/clothing/under/O in world)
|
||||
qdel(O)
|
||||
/datum/admin_secret_item/fun_secret/remove_internal_clothing
|
||||
name = "Remove 'Internal' Clothing"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/remove_internal_clothing/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/obj/item/clothing/under/O in world)
|
||||
qdel(O)
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
/datum/admin_secret_item/fun_secret/send_strike_team
|
||||
name = "Send Strike Team"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/send_strike_team/can_execute(var/mob/user)
|
||||
if(!ticker) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/fun_secret/send_strike_team/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
return user.client.strike_team()
|
||||
/datum/admin_secret_item/fun_secret/send_strike_team
|
||||
name = "Send Strike Team"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/send_strike_team/can_execute(var/mob/user)
|
||||
if(!ticker) return 0
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/fun_secret/send_strike_team/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
return user.client.strike_team()
|
||||
|
||||
@@ -1,21 +1,21 @@
|
||||
/datum/admin_secret_item/fun_secret/toggle_bomb_cap
|
||||
name = "Toggle Bomb Cap"
|
||||
permissions = R_SERVER
|
||||
|
||||
/datum/admin_secret_item/fun_secret/toggle_bomb_cap/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
switch(max_explosion_range)
|
||||
if(14) max_explosion_range = 16
|
||||
if(16) max_explosion_range = 20
|
||||
if(20) max_explosion_range = 28
|
||||
if(28) max_explosion_range = 56
|
||||
if(56) max_explosion_range = 128
|
||||
if(128) max_explosion_range = 14
|
||||
var/range_dev = max_explosion_range *0.25
|
||||
var/range_high = max_explosion_range *0.5
|
||||
var/range_low = max_explosion_range
|
||||
message_admins("<span class='danger'>[key_name_admin(user)] changed the bomb cap to [range_dev], [range_high], [range_low]</span>", 1)
|
||||
log_admin("[key_name_admin(user)] changed the bomb cap to [max_explosion_range]")
|
||||
/datum/admin_secret_item/fun_secret/toggle_bomb_cap
|
||||
name = "Toggle Bomb Cap"
|
||||
permissions = R_SERVER
|
||||
|
||||
/datum/admin_secret_item/fun_secret/toggle_bomb_cap/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
switch(max_explosion_range)
|
||||
if(14) max_explosion_range = 16
|
||||
if(16) max_explosion_range = 20
|
||||
if(20) max_explosion_range = 28
|
||||
if(28) max_explosion_range = 56
|
||||
if(56) max_explosion_range = 128
|
||||
if(128) max_explosion_range = 14
|
||||
var/range_dev = max_explosion_range *0.25
|
||||
var/range_high = max_explosion_range *0.5
|
||||
var/range_low = max_explosion_range
|
||||
message_admins("<span class='danger'>[key_name_admin(user)] changed the bomb cap to [range_dev], [range_high], [range_low]</span>", 1)
|
||||
log_admin("[key_name_admin(user)] changed the bomb cap to [max_explosion_range]")
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
/datum/admin_secret_item/fun_secret/triple_ai_mode
|
||||
name = "Triple AI Mode"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/triple_ai_mode/can_execute(var/mob/user)
|
||||
if(ticker && ticker.current_state > GAME_STATE_PREGAME)
|
||||
return 0
|
||||
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/triple_ai_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
user.client.triple_ai()
|
||||
/datum/admin_secret_item/fun_secret/triple_ai_mode
|
||||
name = "Triple AI Mode"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/triple_ai_mode/can_execute(var/mob/user)
|
||||
if(ticker && ticker.current_state > GAME_STATE_PREGAME)
|
||||
return 0
|
||||
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/admin_secret/triple_ai_mode/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
user.client.triple_ai()
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_corgies
|
||||
name = "Turn All Humans Into Corgies"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_corgies/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
spawn(0)
|
||||
H.corgize()
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_corgies
|
||||
name = "Turn All Humans Into Corgies"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_corgies/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
spawn(0)
|
||||
H.corgize()
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_monkeys
|
||||
name = "Turn All Humans Into Monkeys"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_monkeys/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
spawn(0)
|
||||
H.monkeyize()
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_monkeys
|
||||
name = "Turn All Humans Into Monkeys"
|
||||
|
||||
/datum/admin_secret_item/fun_secret/turn_humans_into_monkeys/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
for(var/mob/living/carbon/human/H in mob_list)
|
||||
spawn(0)
|
||||
H.monkeyize()
|
||||
|
||||
@@ -1,31 +1,31 @@
|
||||
/**********
|
||||
* Gravity *
|
||||
**********/
|
||||
/datum/admin_secret_item/random_event/gravity
|
||||
name = "Toggle Station Artificial Gravity"
|
||||
|
||||
/datum/admin_secret_item/random_event/gravity/can_execute(var/mob/user)
|
||||
if(!(ticker && ticker.mode))
|
||||
return 0
|
||||
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/random_event/gravity/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
gravity_is_on = !gravity_is_on
|
||||
for(var/area/A in world)
|
||||
A.gravitychange(gravity_is_on)
|
||||
|
||||
feedback_inc("admin_secrets_fun_used",1)
|
||||
feedback_add_details("admin_secrets_fun_used","Grav")
|
||||
if(gravity_is_on)
|
||||
log_admin("[key_name(user)] toggled gravity on.", 1)
|
||||
message_admins("<span class='notice'>[key_name_admin(user)] toggled gravity on.</span>", 1)
|
||||
command_announcement.Announce("Gravity generators are again functioning within normal parameters. Sorry for any inconvenience.")
|
||||
else
|
||||
log_admin("[key_name(user)] toggled gravity off.", 1)
|
||||
message_admins("<span class='notice'>[key_name_admin(usr)] toggled gravity off.</span>", 1)
|
||||
command_announcement.Announce("Feedback surge detected in mass-distributions systems. Artificial gravity has been disabled whilst the system reinitializes. Further failures may result in a gravitational collapse and formation of blackholes. Have a nice day.")
|
||||
/**********
|
||||
* Gravity *
|
||||
**********/
|
||||
/datum/admin_secret_item/random_event/gravity
|
||||
name = "Toggle Station Artificial Gravity"
|
||||
|
||||
/datum/admin_secret_item/random_event/gravity/can_execute(var/mob/user)
|
||||
if(!(ticker && ticker.mode))
|
||||
return 0
|
||||
|
||||
return ..()
|
||||
|
||||
/datum/admin_secret_item/random_event/gravity/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return
|
||||
|
||||
gravity_is_on = !gravity_is_on
|
||||
for(var/area/A in world)
|
||||
A.gravitychange(gravity_is_on)
|
||||
|
||||
feedback_inc("admin_secrets_fun_used",1)
|
||||
feedback_add_details("admin_secrets_fun_used","Grav")
|
||||
if(gravity_is_on)
|
||||
log_admin("[key_name(user)] toggled gravity on.", 1)
|
||||
message_admins("<span class='notice'>[key_name_admin(user)] toggled gravity on.</span>", 1)
|
||||
command_announcement.Announce("Gravity generators are again functioning within normal parameters. Sorry for any inconvenience.")
|
||||
else
|
||||
log_admin("[key_name(user)] toggled gravity off.", 1)
|
||||
message_admins("<span class='notice'>[key_name_admin(usr)] toggled gravity off.</span>", 1)
|
||||
command_announcement.Announce("Feedback surge detected in mass-distributions systems. Artificial gravity has been disabled whilst the system reinitializes. Further failures may result in a gravitational collapse and formation of blackholes. Have a nice day.")
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/admin_secret_item/random_event/trigger_cordical_borer_infestation
|
||||
name = "Trigger a Cortical Borer infestation"
|
||||
|
||||
/datum/admin_secret_item/random_event/trigger_cordical_borer_infestation/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
return borers.attempt_random_spawn()
|
||||
/datum/admin_secret_item/random_event/trigger_cordical_borer_infestation
|
||||
name = "Trigger a Cortical Borer infestation"
|
||||
|
||||
/datum/admin_secret_item/random_event/trigger_cordical_borer_infestation/execute(var/mob/user)
|
||||
. = ..()
|
||||
if(.)
|
||||
return borers.attempt_random_spawn()
|
||||
|
||||
@@ -1,36 +1,36 @@
|
||||
/proc/getbrokeninhands()
|
||||
var/icon/IL = new('icons/mob/items/lefthand.dmi')
|
||||
var/list/Lstates = IL.IconStates()
|
||||
var/icon/IR = new('icons/mob/items/righthand.dmi')
|
||||
var/list/Rstates = IR.IconStates()
|
||||
|
||||
|
||||
var/text
|
||||
for(var/A in typesof(/obj/item))
|
||||
var/obj/item/O = new A( locate(1,1,1) )
|
||||
if(!O) continue
|
||||
var/icon/J = new(O.icon)
|
||||
var/list/istates = J.IconStates()
|
||||
if(!Lstates.Find(O.icon_state) && !Lstates.Find(O.item_state))
|
||||
if(O.icon_state)
|
||||
text += "[O.type] is missing left hand icon called \"[O.icon_state]\".\n"
|
||||
if(!Rstates.Find(O.icon_state) && !Rstates.Find(O.item_state))
|
||||
if(O.icon_state)
|
||||
text += "[O.type] is missing right hand icon called \"[O.icon_state]\".\n"
|
||||
|
||||
|
||||
if(O.icon_state)
|
||||
if(!istates.Find(O.icon_state))
|
||||
text += "[O.type] is missing normal icon called \"[O.icon_state]\" in \"[O.icon]\".\n"
|
||||
//if(O.item_state)
|
||||
// if(!istates.Find(O.item_state))
|
||||
// text += "[O.type] MISSING NORMAL ICON CALLED\n\"[O.item_state]\" IN \"[O.icon]\"\n"
|
||||
//text+="\n"
|
||||
qdel(O)
|
||||
if(text)
|
||||
var/F = file("broken_icons.txt")
|
||||
fdel(F)
|
||||
F << text
|
||||
to_world("<span class='filter_system'>Completeled successfully and written to [F]</span>")
|
||||
|
||||
|
||||
/proc/getbrokeninhands()
|
||||
var/icon/IL = new('icons/mob/items/lefthand.dmi')
|
||||
var/list/Lstates = IL.IconStates()
|
||||
var/icon/IR = new('icons/mob/items/righthand.dmi')
|
||||
var/list/Rstates = IR.IconStates()
|
||||
|
||||
|
||||
var/text
|
||||
for(var/A in typesof(/obj/item))
|
||||
var/obj/item/O = new A( locate(1,1,1) )
|
||||
if(!O) continue
|
||||
var/icon/J = new(O.icon)
|
||||
var/list/istates = J.IconStates()
|
||||
if(!Lstates.Find(O.icon_state) && !Lstates.Find(O.item_state))
|
||||
if(O.icon_state)
|
||||
text += "[O.type] is missing left hand icon called \"[O.icon_state]\".\n"
|
||||
if(!Rstates.Find(O.icon_state) && !Rstates.Find(O.item_state))
|
||||
if(O.icon_state)
|
||||
text += "[O.type] is missing right hand icon called \"[O.icon_state]\".\n"
|
||||
|
||||
|
||||
if(O.icon_state)
|
||||
if(!istates.Find(O.icon_state))
|
||||
text += "[O.type] is missing normal icon called \"[O.icon_state]\" in \"[O.icon]\".\n"
|
||||
//if(O.item_state)
|
||||
// if(!istates.Find(O.item_state))
|
||||
// text += "[O.type] MISSING NORMAL ICON CALLED\n\"[O.item_state]\" IN \"[O.icon]\"\n"
|
||||
//text+="\n"
|
||||
qdel(O)
|
||||
if(text)
|
||||
var/F = file("broken_icons.txt")
|
||||
fdel(F)
|
||||
F << text
|
||||
to_world("<span class='filter_system'>Completeled successfully and written to [F]</span>")
|
||||
|
||||
|
||||
|
||||
@@ -1,63 +1,63 @@
|
||||
/client/proc/cmd_admin_say(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Asay" //Gave this shit a shorter name so you only have to time out "asay" rather than "admin say" to use it --NeoFite
|
||||
set hidden = 1
|
||||
if(!check_rights(R_ADMIN)) //VOREStation Edit
|
||||
return
|
||||
|
||||
msg = sanitize(msg)
|
||||
if(!msg)
|
||||
return
|
||||
|
||||
log_adminsay(msg,src)
|
||||
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(check_rights(R_ADMIN, 0, C))
|
||||
to_chat(C, "<span class='admin_channel'>" + create_text_tag("admin", "ADMIN:", C) + " <span class='name'>[key_name(usr, 1)]</span>([admin_jump_link(mob, src)]): <span class='message'>[msg]</span></span>")
|
||||
|
||||
feedback_add_details("admin_verb","M") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/cmd_mod_say(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Msay"
|
||||
set hidden = 1
|
||||
|
||||
if(!check_rights(R_ADMIN|R_MOD|R_SERVER)) //VOREStation Edit
|
||||
return
|
||||
|
||||
msg = sanitize(msg)
|
||||
log_modsay(msg,src)
|
||||
|
||||
if (!msg)
|
||||
return
|
||||
|
||||
var/sender_name = key_name(usr, 1)
|
||||
if(check_rights(R_ADMIN, 0))
|
||||
sender_name = "<span class='admin'>[sender_name]</span>"
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(check_rights(R_ADMIN|R_MOD|R_SERVER, 0, C)) //VOREStation Edit //YW Edit, fix issue with C missing from check_rights, so all admins could see mchat
|
||||
to_chat(C, "<span class='mod_channel'>" + create_text_tag("mod", "MOD:", C) + " <span class='name'>[sender_name]</span>([admin_jump_link(mob, C.holder)]): <span class='message'>[msg]</span></span>")
|
||||
|
||||
feedback_add_details("admin_verb","MS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/cmd_event_say(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Esay"
|
||||
set hidden = 1
|
||||
|
||||
if(!check_rights(R_ADMIN|R_MOD|R_EVENT|R_SERVER)) //VOREStation Edit
|
||||
return
|
||||
|
||||
msg = sanitize(msg)
|
||||
log_eventsay(msg,src)
|
||||
|
||||
if (!msg)
|
||||
return
|
||||
|
||||
var/sender_name = key_name(usr, 1)
|
||||
if(check_rights(R_ADMIN, 0))
|
||||
sender_name = "<span class='admin'>[sender_name]</span>"
|
||||
for(var/client/C in GLOB.admins)
|
||||
to_chat(C, "<span class='event_channel'>" + create_text_tag("event", "EVENT:", C) + " <span class='name'>[sender_name]</span>([admin_jump_link(mob, C.holder)]): <span class='message'>[msg]</span></span>")
|
||||
|
||||
feedback_add_details("admin_verb","GS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
/client/proc/cmd_admin_say(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Asay" //Gave this shit a shorter name so you only have to time out "asay" rather than "admin say" to use it --NeoFite
|
||||
set hidden = 1
|
||||
if(!check_rights(R_ADMIN)) //VOREStation Edit
|
||||
return
|
||||
|
||||
msg = sanitize(msg)
|
||||
if(!msg)
|
||||
return
|
||||
|
||||
log_adminsay(msg,src)
|
||||
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(check_rights(R_ADMIN, 0, C))
|
||||
to_chat(C, "<span class='admin_channel'>" + create_text_tag("admin", "ADMIN:", C) + " <span class='name'>[key_name(usr, 1)]</span>([admin_jump_link(mob, src)]): <span class='message'>[msg]</span></span>")
|
||||
|
||||
feedback_add_details("admin_verb","M") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/cmd_mod_say(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Msay"
|
||||
set hidden = 1
|
||||
|
||||
if(!check_rights(R_ADMIN|R_MOD|R_SERVER)) //VOREStation Edit
|
||||
return
|
||||
|
||||
msg = sanitize(msg)
|
||||
log_modsay(msg,src)
|
||||
|
||||
if (!msg)
|
||||
return
|
||||
|
||||
var/sender_name = key_name(usr, 1)
|
||||
if(check_rights(R_ADMIN, 0))
|
||||
sender_name = "<span class='admin'>[sender_name]</span>"
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(check_rights(R_ADMIN|R_MOD|R_SERVER, 0, C)) //VOREStation Edit //YW Edit, fix issue with C missing from check_rights, so all admins could see mchat
|
||||
to_chat(C, "<span class='mod_channel'>" + create_text_tag("mod", "MOD:", C) + " <span class='name'>[sender_name]</span>([admin_jump_link(mob, C.holder)]): <span class='message'>[msg]</span></span>")
|
||||
|
||||
feedback_add_details("admin_verb","MS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/cmd_event_say(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Esay"
|
||||
set hidden = 1
|
||||
|
||||
if(!check_rights(R_ADMIN|R_MOD|R_EVENT|R_SERVER)) //VOREStation Edit
|
||||
return
|
||||
|
||||
msg = sanitize(msg)
|
||||
log_eventsay(msg,src)
|
||||
|
||||
if (!msg)
|
||||
return
|
||||
|
||||
var/sender_name = key_name(usr, 1)
|
||||
if(check_rights(R_ADMIN, 0))
|
||||
sender_name = "<span class='admin'>[sender_name]</span>"
|
||||
for(var/client/C in GLOB.admins)
|
||||
to_chat(C, "<span class='event_channel'>" + create_text_tag("event", "EVENT:", C) + " <span class='name'>[sender_name]</span>([admin_jump_link(mob, C.holder)]): <span class='message'>[msg]</span></span>")
|
||||
|
||||
feedback_add_details("admin_verb","GS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
@@ -1,60 +1,60 @@
|
||||
/client/proc/atmosscan()
|
||||
set category = "Mapping"
|
||||
set name = "Check Piping"
|
||||
set background = 1
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
feedback_add_details("admin_verb","CP") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
if(tgui_alert(usr, "WARNING: This command should not be run on a live server. Do you want to continue?", "Check Piping", list("No", "Yes")) == "No")
|
||||
return
|
||||
|
||||
to_chat(usr, "Checking for disconnected pipes...")
|
||||
//all plumbing - yes, some things might get stated twice, doesn't matter.
|
||||
for (var/obj/machinery/atmospherics/plumbing in machines)
|
||||
if (plumbing.nodealert)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Unconnected [plumbing.name] located at [plumbing.x],[plumbing.y],[plumbing.z] ([get_area(plumbing.loc)])</span>")
|
||||
|
||||
//Manifolds
|
||||
for (var/obj/machinery/atmospherics/pipe/manifold/pipe in machines)
|
||||
if (!pipe.node1 || !pipe.node2 || !pipe.node3)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Unconnected [pipe.name] located at [pipe.x],[pipe.y],[pipe.z] ([get_area(pipe.loc)])</span>")
|
||||
|
||||
//Pipes
|
||||
for (var/obj/machinery/atmospherics/pipe/simple/pipe in machines)
|
||||
if (!pipe.node1 || !pipe.node2)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Unconnected [pipe.name] located at [pipe.x],[pipe.y],[pipe.z] ([get_area(pipe.loc)])</span>")
|
||||
|
||||
to_chat(usr, "Checking for overlapping pipes...")
|
||||
next_turf:
|
||||
for(var/turf/T in world)
|
||||
for(var/dir in cardinal)
|
||||
var/list/connect_types = list(1 = 0, 2 = 0, 3 = 0)
|
||||
for(var/obj/machinery/atmospherics/pipe in T)
|
||||
if(dir & pipe.initialize_directions)
|
||||
for(var/connect_type in pipe.connect_types)
|
||||
connect_types[connect_type] += 1
|
||||
if(connect_types[1] > 1 || connect_types[2] > 1 || connect_types[3] > 1)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Overlapping pipe ([pipe.name]) located at [T.x],[T.y],[T.z] ([get_area(T)])</span>")
|
||||
continue next_turf
|
||||
to_chat(usr, "Done")
|
||||
|
||||
/client/proc/powerdebug()
|
||||
set category = "Mapping"
|
||||
set name = "Check Power"
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
feedback_add_details("admin_verb","CPOW") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
for (var/datum/powernet/PN in powernets)
|
||||
if (!PN.nodes || !PN.nodes.len)
|
||||
if(PN.cables && (PN.cables.len > 1))
|
||||
var/obj/structure/cable/C = PN.cables[1]
|
||||
to_chat(usr, "<span class='filter_adminlog'>Powernet with no nodes! (number [PN.number]) - example cable at [C.x], [C.y], [C.z] in area [get_area(C.loc)]</span>")
|
||||
|
||||
if (!PN.cables || (PN.cables.len < 10))
|
||||
if(PN.cables && (PN.cables.len > 1))
|
||||
var/obj/structure/cable/C = PN.cables[1]
|
||||
/client/proc/atmosscan()
|
||||
set category = "Mapping"
|
||||
set name = "Check Piping"
|
||||
set background = 1
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
feedback_add_details("admin_verb","CP") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
if(tgui_alert(usr, "WARNING: This command should not be run on a live server. Do you want to continue?", "Check Piping", list("No", "Yes")) == "No")
|
||||
return
|
||||
|
||||
to_chat(usr, "Checking for disconnected pipes...")
|
||||
//all plumbing - yes, some things might get stated twice, doesn't matter.
|
||||
for (var/obj/machinery/atmospherics/plumbing in machines)
|
||||
if (plumbing.nodealert)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Unconnected [plumbing.name] located at [plumbing.x],[plumbing.y],[plumbing.z] ([get_area(plumbing.loc)])</span>")
|
||||
|
||||
//Manifolds
|
||||
for (var/obj/machinery/atmospherics/pipe/manifold/pipe in machines)
|
||||
if (!pipe.node1 || !pipe.node2 || !pipe.node3)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Unconnected [pipe.name] located at [pipe.x],[pipe.y],[pipe.z] ([get_area(pipe.loc)])</span>")
|
||||
|
||||
//Pipes
|
||||
for (var/obj/machinery/atmospherics/pipe/simple/pipe in machines)
|
||||
if (!pipe.node1 || !pipe.node2)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Unconnected [pipe.name] located at [pipe.x],[pipe.y],[pipe.z] ([get_area(pipe.loc)])</span>")
|
||||
|
||||
to_chat(usr, "Checking for overlapping pipes...")
|
||||
next_turf:
|
||||
for(var/turf/T in world)
|
||||
for(var/dir in cardinal)
|
||||
var/list/connect_types = list(1 = 0, 2 = 0, 3 = 0)
|
||||
for(var/obj/machinery/atmospherics/pipe in T)
|
||||
if(dir & pipe.initialize_directions)
|
||||
for(var/connect_type in pipe.connect_types)
|
||||
connect_types[connect_type] += 1
|
||||
if(connect_types[1] > 1 || connect_types[2] > 1 || connect_types[3] > 1)
|
||||
to_chat(usr, "<span class='filter_adminlog warning'>Overlapping pipe ([pipe.name]) located at [T.x],[T.y],[T.z] ([get_area(T)])</span>")
|
||||
continue next_turf
|
||||
to_chat(usr, "Done")
|
||||
|
||||
/client/proc/powerdebug()
|
||||
set category = "Mapping"
|
||||
set name = "Check Power"
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
feedback_add_details("admin_verb","CPOW") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
for (var/datum/powernet/PN in powernets)
|
||||
if (!PN.nodes || !PN.nodes.len)
|
||||
if(PN.cables && (PN.cables.len > 1))
|
||||
var/obj/structure/cable/C = PN.cables[1]
|
||||
to_chat(usr, "<span class='filter_adminlog'>Powernet with no nodes! (number [PN.number]) - example cable at [C.x], [C.y], [C.z] in area [get_area(C.loc)]</span>")
|
||||
|
||||
if (!PN.cables || (PN.cables.len < 10))
|
||||
if(PN.cables && (PN.cables.len > 1))
|
||||
var/obj/structure/cable/C = PN.cables[1]
|
||||
to_chat(usr, "<span class='filter_adminlog'>Powernet with fewer than 10 cables! (number [PN.number]) - example cable at [C.x], [C.y], [C.z] in area [get_area(C.loc)]</span>")
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,31 +1,31 @@
|
||||
/client/proc/dsay(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Dsay" //Gave this shit a shorter name so you only have to time out "dsay" rather than "dead say" to use it --NeoFite
|
||||
set hidden = 1
|
||||
if(!src.holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
if(!src.mob)
|
||||
return
|
||||
if(prefs.muted & MUTE_DEADCHAT)
|
||||
to_chat(src, "<span class='warning'>You cannot send DSAY messages (muted).</span>")
|
||||
return
|
||||
|
||||
if(!is_preference_enabled(/datum/client_preference/show_dsay))
|
||||
to_chat(src, "<span class='warning'>You have deadchat muted.</span>")
|
||||
return
|
||||
|
||||
if (src.handle_spam_prevention(msg,MUTE_DEADCHAT))
|
||||
return
|
||||
|
||||
var/stafftype = uppertext(holder.rank)
|
||||
|
||||
msg = sanitize(msg)
|
||||
log_admin("DSAY: [key_name(src)] : [msg]")
|
||||
|
||||
if (!msg)
|
||||
return
|
||||
|
||||
say_dead_direct("<span class='name'>[stafftype]([src.holder.fakekey ? src.holder.fakekey : src.key])</span> says, <span class='message'>\"[msg]\"</span>")
|
||||
|
||||
feedback_add_details("admin_verb","D") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
/client/proc/dsay(msg as text)
|
||||
set category = "Special Verbs"
|
||||
set name = "Dsay" //Gave this shit a shorter name so you only have to time out "dsay" rather than "dead say" to use it --NeoFite
|
||||
set hidden = 1
|
||||
if(!src.holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
if(!src.mob)
|
||||
return
|
||||
if(prefs.muted & MUTE_DEADCHAT)
|
||||
to_chat(src, "<span class='warning'>You cannot send DSAY messages (muted).</span>")
|
||||
return
|
||||
|
||||
if(!is_preference_enabled(/datum/client_preference/show_dsay))
|
||||
to_chat(src, "<span class='warning'>You have deadchat muted.</span>")
|
||||
return
|
||||
|
||||
if (src.handle_spam_prevention(msg,MUTE_DEADCHAT))
|
||||
return
|
||||
|
||||
var/stafftype = uppertext(holder.rank)
|
||||
|
||||
msg = sanitize(msg)
|
||||
log_admin("DSAY: [key_name(src)] : [msg]")
|
||||
|
||||
if (!msg)
|
||||
return
|
||||
|
||||
say_dead_direct("<span class='name'>[stafftype]([src.holder.fakekey ? src.holder.fakekey : src.key])</span> says, <span class='message'>\"[msg]\"</span>")
|
||||
|
||||
feedback_add_details("admin_verb","D") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
@@ -1,187 +1,187 @@
|
||||
/client/proc/air_report()
|
||||
set category = "Debug"
|
||||
set name = "Show Air Report"
|
||||
|
||||
if(!master_controller || !air_master)
|
||||
tgui_alert_async(usr,"Master_controller or air_master not found.","Air Report")
|
||||
return
|
||||
|
||||
var/active_groups = air_master.active_zones
|
||||
var/inactive_groups = air_master.zones.len - active_groups
|
||||
|
||||
var/hotspots = 0
|
||||
for(var/obj/fire/hotspot in world)
|
||||
hotspots++
|
||||
|
||||
var/active_on_main_station = 0
|
||||
var/inactive_on_main_station = 0
|
||||
for(var/zone/zone in air_master.zones)
|
||||
var/turf/simulated/turf = locate() in zone.contents
|
||||
if(turf?.z in using_map.station_levels)
|
||||
if(zone.needs_update)
|
||||
active_on_main_station++
|
||||
else
|
||||
inactive_on_main_station++
|
||||
|
||||
var/output = {"<B>AIR SYSTEMS REPORT</B><HR>
|
||||
<B>General Processing Data</B><BR>
|
||||
Cycle: [air_master.current_cycle]<br>
|
||||
Groups: [air_master.zones.len]<BR>
|
||||
---- <I>Active:</I> [active_groups]<BR>
|
||||
---- <I>Inactive:</I> [inactive_groups]<BR><br>
|
||||
---- <I>Active on station:</i> [active_on_main_station]<br>
|
||||
---- <i>Inactive on station:</i> [inactive_on_main_station]<br>
|
||||
<BR>
|
||||
<B>Special Processing Data</B><BR>
|
||||
Hotspot Processing: [hotspots]<BR>
|
||||
<br>
|
||||
<B>Geometry Processing Data</B><BR>
|
||||
Tile Update: [air_master.tiles_to_update.len]<BR>
|
||||
"}
|
||||
|
||||
usr << browse(output,"window=airreport")
|
||||
|
||||
/client/proc/fix_next_move()
|
||||
set category = "Debug"
|
||||
set name = "Unfreeze Everyone"
|
||||
var/largest_move_time = 0
|
||||
var/largest_click_time = 0
|
||||
var/mob/largest_move_mob = null
|
||||
var/mob/largest_click_mob = null
|
||||
for(var/mob/M in mob_list)
|
||||
if(!M.client)
|
||||
continue
|
||||
if(M.next_move >= largest_move_time)
|
||||
largest_move_mob = M
|
||||
if(M.next_move > world.time)
|
||||
largest_move_time = M.next_move - world.time
|
||||
else
|
||||
largest_move_time = 1
|
||||
if(M.next_click >= largest_click_time)
|
||||
largest_click_mob = M
|
||||
if(M.next_click > world.time)
|
||||
largest_click_time = M.next_click - world.time
|
||||
else
|
||||
largest_click_time = 0
|
||||
log_admin("DEBUG: [key_name(M)] next_move = [M.next_move] next_click = [M.next_click] world.time = [world.time]")
|
||||
M.next_move = 1
|
||||
M.next_click = 0
|
||||
message_admins("[key_name_admin(largest_move_mob)] had the largest move delay with [largest_move_time] frames / [largest_move_time/10] seconds!", 1)
|
||||
message_admins("[key_name_admin(largest_click_mob)] had the largest click delay with [largest_click_time] frames / [largest_click_time/10] seconds!", 1)
|
||||
message_admins("world.time = [world.time]", 1)
|
||||
feedback_add_details("admin_verb","UFE") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
return
|
||||
|
||||
/client/proc/radio_report()
|
||||
set category = "Debug"
|
||||
set name = "Radio report"
|
||||
|
||||
var/output = "<b>Radio Report</b><hr>"
|
||||
for (var/fq in radio_controller.frequencies)
|
||||
output += "<b>Freq: [fq]</b><br>"
|
||||
var/datum/radio_frequency/fqs = radio_controller.frequencies[fq]
|
||||
if (!fqs)
|
||||
output += " <b>ERROR</b><br>"
|
||||
continue
|
||||
for (var/radio_filter in fqs.devices)
|
||||
var/list/f = fqs.devices[radio_filter]
|
||||
if (!f)
|
||||
output += " [radio_filter]: ERROR<br>"
|
||||
continue
|
||||
output += " [radio_filter]: [f.len]<br>"
|
||||
for (var/device in f)
|
||||
if (isobj(device))
|
||||
output += " [device] ([device:x],[device:y],[device:z] in area [get_area(device:loc)])<br>"
|
||||
else
|
||||
output += " [device]<br>"
|
||||
|
||||
usr << browse(output,"window=radioreport")
|
||||
feedback_add_details("admin_verb","RR") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/reload_admins()
|
||||
set name = "Reload Admins"
|
||||
set category = "Debug"
|
||||
|
||||
if(!check_rights(R_SERVER)) return
|
||||
|
||||
message_admins("[usr] manually reloaded admins")
|
||||
load_admins()
|
||||
feedback_add_details("admin_verb","RLDA") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/reload_eventMs()
|
||||
set name = "Reload Event Managers"
|
||||
set category = "Debug"
|
||||
|
||||
if(!check_rights(R_SERVER)) return
|
||||
|
||||
message_admins("[usr] manually reloaded Event Managers")
|
||||
world.load_mods()
|
||||
|
||||
|
||||
//todo:
|
||||
/client/proc/jump_to_dead_group()
|
||||
set name = "Jump to dead group"
|
||||
set category = "Debug"
|
||||
/*
|
||||
if(!holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
|
||||
if(!air_master)
|
||||
to_chat(usr, "Cannot find air_system")
|
||||
return
|
||||
var/datum/air_group/dead_groups = list()
|
||||
for(var/datum/air_group/group in air_master.air_groups)
|
||||
if (!group.group_processing)
|
||||
dead_groups += group
|
||||
var/datum/air_group/dest_group = pick(dead_groups)
|
||||
usr.loc = pick(dest_group.members)
|
||||
feedback_add_details("admin_verb","JDAG") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
return
|
||||
*/
|
||||
|
||||
/client/proc/kill_airgroup()
|
||||
set name = "Kill Local Airgroup"
|
||||
set desc = "Use this to allow manual manupliation of atmospherics."
|
||||
set category = "Debug"
|
||||
/*
|
||||
if(!holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
|
||||
if(!air_master)
|
||||
to_chat(usr, "Cannot find air_system")
|
||||
return
|
||||
|
||||
var/turf/T = get_turf(usr)
|
||||
if(istype(T, /turf/simulated))
|
||||
var/datum/air_group/AG = T:parent
|
||||
AG.next_check = 30
|
||||
AG.group_processing = 0
|
||||
else
|
||||
to_chat(usr, "Local airgroup is unsimulated!")
|
||||
feedback_add_details("admin_verb","KLAG") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
*/
|
||||
|
||||
/client/proc/print_jobban_old()
|
||||
set name = "Print Jobban Log"
|
||||
set desc = "This spams all the active jobban entries for the current round to standard output."
|
||||
set category = "Debug"
|
||||
|
||||
to_chat(usr, "<b>Jobbans active in this round.</b>")
|
||||
for(var/t in jobban_keylist)
|
||||
to_chat(usr, "[t]")
|
||||
|
||||
/client/proc/print_jobban_old_filter()
|
||||
set name = "Search Jobban Log"
|
||||
set desc = "This searches all the active jobban entries for the current round and outputs the results to standard output."
|
||||
set category = "Debug"
|
||||
|
||||
var/job_filter = tgui_input_text(usr, "Contains what?","Job Filter")
|
||||
if(!job_filter)
|
||||
return
|
||||
|
||||
to_chat(usr, "<b>Jobbans active in this round.</b>")
|
||||
for(var/t in jobban_keylist)
|
||||
if(findtext(t, job_filter))
|
||||
to_chat(usr, "[t]")
|
||||
/client/proc/air_report()
|
||||
set category = "Debug"
|
||||
set name = "Show Air Report"
|
||||
|
||||
if(!master_controller || !air_master)
|
||||
tgui_alert_async(usr,"Master_controller or air_master not found.","Air Report")
|
||||
return
|
||||
|
||||
var/active_groups = air_master.active_zones
|
||||
var/inactive_groups = air_master.zones.len - active_groups
|
||||
|
||||
var/hotspots = 0
|
||||
for(var/obj/fire/hotspot in world)
|
||||
hotspots++
|
||||
|
||||
var/active_on_main_station = 0
|
||||
var/inactive_on_main_station = 0
|
||||
for(var/zone/zone in air_master.zones)
|
||||
var/turf/simulated/turf = locate() in zone.contents
|
||||
if(turf?.z in using_map.station_levels)
|
||||
if(zone.needs_update)
|
||||
active_on_main_station++
|
||||
else
|
||||
inactive_on_main_station++
|
||||
|
||||
var/output = {"<B>AIR SYSTEMS REPORT</B><HR>
|
||||
<B>General Processing Data</B><BR>
|
||||
Cycle: [air_master.current_cycle]<br>
|
||||
Groups: [air_master.zones.len]<BR>
|
||||
---- <I>Active:</I> [active_groups]<BR>
|
||||
---- <I>Inactive:</I> [inactive_groups]<BR><br>
|
||||
---- <I>Active on station:</i> [active_on_main_station]<br>
|
||||
---- <i>Inactive on station:</i> [inactive_on_main_station]<br>
|
||||
<BR>
|
||||
<B>Special Processing Data</B><BR>
|
||||
Hotspot Processing: [hotspots]<BR>
|
||||
<br>
|
||||
<B>Geometry Processing Data</B><BR>
|
||||
Tile Update: [air_master.tiles_to_update.len]<BR>
|
||||
"}
|
||||
|
||||
usr << browse(output,"window=airreport")
|
||||
|
||||
/client/proc/fix_next_move()
|
||||
set category = "Debug"
|
||||
set name = "Unfreeze Everyone"
|
||||
var/largest_move_time = 0
|
||||
var/largest_click_time = 0
|
||||
var/mob/largest_move_mob = null
|
||||
var/mob/largest_click_mob = null
|
||||
for(var/mob/M in mob_list)
|
||||
if(!M.client)
|
||||
continue
|
||||
if(M.next_move >= largest_move_time)
|
||||
largest_move_mob = M
|
||||
if(M.next_move > world.time)
|
||||
largest_move_time = M.next_move - world.time
|
||||
else
|
||||
largest_move_time = 1
|
||||
if(M.next_click >= largest_click_time)
|
||||
largest_click_mob = M
|
||||
if(M.next_click > world.time)
|
||||
largest_click_time = M.next_click - world.time
|
||||
else
|
||||
largest_click_time = 0
|
||||
log_admin("DEBUG: [key_name(M)] next_move = [M.next_move] next_click = [M.next_click] world.time = [world.time]")
|
||||
M.next_move = 1
|
||||
M.next_click = 0
|
||||
message_admins("[key_name_admin(largest_move_mob)] had the largest move delay with [largest_move_time] frames / [largest_move_time/10] seconds!", 1)
|
||||
message_admins("[key_name_admin(largest_click_mob)] had the largest click delay with [largest_click_time] frames / [largest_click_time/10] seconds!", 1)
|
||||
message_admins("world.time = [world.time]", 1)
|
||||
feedback_add_details("admin_verb","UFE") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
return
|
||||
|
||||
/client/proc/radio_report()
|
||||
set category = "Debug"
|
||||
set name = "Radio report"
|
||||
|
||||
var/output = "<b>Radio Report</b><hr>"
|
||||
for (var/fq in radio_controller.frequencies)
|
||||
output += "<b>Freq: [fq]</b><br>"
|
||||
var/datum/radio_frequency/fqs = radio_controller.frequencies[fq]
|
||||
if (!fqs)
|
||||
output += " <b>ERROR</b><br>"
|
||||
continue
|
||||
for (var/radio_filter in fqs.devices)
|
||||
var/list/f = fqs.devices[radio_filter]
|
||||
if (!f)
|
||||
output += " [radio_filter]: ERROR<br>"
|
||||
continue
|
||||
output += " [radio_filter]: [f.len]<br>"
|
||||
for (var/device in f)
|
||||
if (isobj(device))
|
||||
output += " [device] ([device:x],[device:y],[device:z] in area [get_area(device:loc)])<br>"
|
||||
else
|
||||
output += " [device]<br>"
|
||||
|
||||
usr << browse(output,"window=radioreport")
|
||||
feedback_add_details("admin_verb","RR") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/reload_admins()
|
||||
set name = "Reload Admins"
|
||||
set category = "Debug"
|
||||
|
||||
if(!check_rights(R_SERVER)) return
|
||||
|
||||
message_admins("[usr] manually reloaded admins")
|
||||
load_admins()
|
||||
feedback_add_details("admin_verb","RLDA") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/reload_eventMs()
|
||||
set name = "Reload Event Managers"
|
||||
set category = "Debug"
|
||||
|
||||
if(!check_rights(R_SERVER)) return
|
||||
|
||||
message_admins("[usr] manually reloaded Event Managers")
|
||||
world.load_mods()
|
||||
|
||||
|
||||
//todo:
|
||||
/client/proc/jump_to_dead_group()
|
||||
set name = "Jump to dead group"
|
||||
set category = "Debug"
|
||||
/*
|
||||
if(!holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
|
||||
if(!air_master)
|
||||
to_chat(usr, "Cannot find air_system")
|
||||
return
|
||||
var/datum/air_group/dead_groups = list()
|
||||
for(var/datum/air_group/group in air_master.air_groups)
|
||||
if (!group.group_processing)
|
||||
dead_groups += group
|
||||
var/datum/air_group/dest_group = pick(dead_groups)
|
||||
usr.loc = pick(dest_group.members)
|
||||
feedback_add_details("admin_verb","JDAG") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
return
|
||||
*/
|
||||
|
||||
/client/proc/kill_airgroup()
|
||||
set name = "Kill Local Airgroup"
|
||||
set desc = "Use this to allow manual manupliation of atmospherics."
|
||||
set category = "Debug"
|
||||
/*
|
||||
if(!holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
|
||||
if(!air_master)
|
||||
to_chat(usr, "Cannot find air_system")
|
||||
return
|
||||
|
||||
var/turf/T = get_turf(usr)
|
||||
if(istype(T, /turf/simulated))
|
||||
var/datum/air_group/AG = T:parent
|
||||
AG.next_check = 30
|
||||
AG.group_processing = 0
|
||||
else
|
||||
to_chat(usr, "Local airgroup is unsimulated!")
|
||||
feedback_add_details("admin_verb","KLAG") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
*/
|
||||
|
||||
/client/proc/print_jobban_old()
|
||||
set name = "Print Jobban Log"
|
||||
set desc = "This spams all the active jobban entries for the current round to standard output."
|
||||
set category = "Debug"
|
||||
|
||||
to_chat(usr, "<b>Jobbans active in this round.</b>")
|
||||
for(var/t in jobban_keylist)
|
||||
to_chat(usr, "[t]")
|
||||
|
||||
/client/proc/print_jobban_old_filter()
|
||||
set name = "Search Jobban Log"
|
||||
set desc = "This searches all the active jobban entries for the current round and outputs the results to standard output."
|
||||
set category = "Debug"
|
||||
|
||||
var/job_filter = tgui_input_text(usr, "Contains what?","Job Filter")
|
||||
if(!job_filter)
|
||||
return
|
||||
|
||||
to_chat(usr, "<b>Jobbans active in this round.</b>")
|
||||
for(var/t in jobban_keylist)
|
||||
if(findtext(t, job_filter))
|
||||
to_chat(usr, "[t]")
|
||||
|
||||
@@ -1,23 +1,23 @@
|
||||
//Merged Doohl's and the existing ticklag as they both had good elements about them ~
|
||||
//Replaces the old Ticklag verb, fps is easier to understand
|
||||
/client/proc/set_server_fps()
|
||||
set category = "Debug"
|
||||
set name = "Set Server FPS"
|
||||
set desc = "Sets game speed in frames-per-second. Can potentially break the game"
|
||||
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
|
||||
var/new_fps = round(tgui_input_number(usr, "Sets game frames-per-second. Can potentially break the game (default: [config.fps])", "FPS", world.fps), round(config.fps * 1.5))
|
||||
if(new_fps <= 0)
|
||||
to_chat(src, "<span class='danger'>Error: set_server_fps(): Invalid world.fps value. No changes made.</span>")
|
||||
return
|
||||
if(new_fps > config.fps * 1.5)
|
||||
if(tgui_alert(src, "You are setting fps to a high value:\n\t[new_fps] frames-per-second\n\tconfig.fps = [config.fps]", "Warning!", list("Confirm", "ABORT-ABORT-ABORT")) != "Confirm")
|
||||
return
|
||||
|
||||
var/msg = "[key_name(src)] has modified world.fps to [new_fps]"
|
||||
log_admin(msg, 0)
|
||||
message_admins(msg, 0)
|
||||
world.change_fps(new_fps)
|
||||
feedback_add_details("admin_verb", "SETFPS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
//Merged Doohl's and the existing ticklag as they both had good elements about them ~
|
||||
//Replaces the old Ticklag verb, fps is easier to understand
|
||||
/client/proc/set_server_fps()
|
||||
set category = "Debug"
|
||||
set name = "Set Server FPS"
|
||||
set desc = "Sets game speed in frames-per-second. Can potentially break the game"
|
||||
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
|
||||
var/new_fps = round(tgui_input_number(usr, "Sets game frames-per-second. Can potentially break the game (default: [config.fps])", "FPS", world.fps), round(config.fps * 1.5))
|
||||
if(new_fps <= 0)
|
||||
to_chat(src, "<span class='danger'>Error: set_server_fps(): Invalid world.fps value. No changes made.</span>")
|
||||
return
|
||||
if(new_fps > config.fps * 1.5)
|
||||
if(tgui_alert(src, "You are setting fps to a high value:\n\t[new_fps] frames-per-second\n\tconfig.fps = [config.fps]", "Warning!", list("Confirm", "ABORT-ABORT-ABORT")) != "Confirm")
|
||||
return
|
||||
|
||||
var/msg = "[key_name(src)] has modified world.fps to [new_fps]"
|
||||
log_admin(msg, 0)
|
||||
message_admins(msg, 0)
|
||||
world.change_fps(new_fps)
|
||||
feedback_add_details("admin_verb", "SETFPS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
@@ -1,311 +1,311 @@
|
||||
//world/proc/shelleo
|
||||
#define SHELLEO_ERRORLEVEL 1
|
||||
#define SHELLEO_STDOUT 2
|
||||
#define SHELLEO_STDERR 3
|
||||
|
||||
var/list/sounds_cache = list()
|
||||
|
||||
/client/proc/play_sound(S as sound)
|
||||
set category = "Fun"
|
||||
set name = "Play Global Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
var/freq = 1
|
||||
var/vol = tgui_input_number(usr, "What volume would you like the sound to play at?",, 100, 100, 1)
|
||||
if(!vol)
|
||||
return
|
||||
vol = clamp(vol, 1, 100)
|
||||
|
||||
var/sound/admin_sound = new()
|
||||
admin_sound.file = S
|
||||
admin_sound.priority = 250
|
||||
admin_sound.channel = 777
|
||||
admin_sound.frequency = freq
|
||||
admin_sound.wait = 1
|
||||
admin_sound.repeat = FALSE
|
||||
admin_sound.status = SOUND_STREAM
|
||||
admin_sound.volume = vol
|
||||
|
||||
sounds_cache += S
|
||||
|
||||
var/res = tgui_alert(usr, "Show the title of this song ([S]) to the players?\nOptions 'Yes' and 'No' will play the sound.",, list("Yes", "No", "Cancel"))
|
||||
switch(res)
|
||||
if("Yes")
|
||||
to_chat(world, "<span class='boldannounce'>An admin played: [S]</span>", confidential = TRUE)
|
||||
if("Cancel")
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] played sound [S]")
|
||||
message_admins("[key_name_admin(src)] played sound [S]", 1)
|
||||
|
||||
for(var/mob/M in player_list)
|
||||
if(M.is_preference_enabled(/datum/client_preference/play_admin_midis))
|
||||
admin_sound.volume = vol * M.client.admin_music_volume
|
||||
SEND_SOUND(M, admin_sound)
|
||||
admin_sound.volume = vol
|
||||
|
||||
feedback_add_details("admin_verb", "Play Global Sound")
|
||||
|
||||
/client/proc/play_local_sound(S as sound)
|
||||
set category = "Fun"
|
||||
set name = "Play Local Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] played a local sound [S]")
|
||||
message_admins("[key_name_admin(src)] played a local sound [S]", 1)
|
||||
playsound(src.mob, S, 50, 0, 0)
|
||||
feedback_add_details("admin_verb", "Play Local Sound")
|
||||
|
||||
/client/proc/play_direct_mob_sound(S as sound, mob/M)
|
||||
set category = "Fun"
|
||||
set name = "Play Direct Mob Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
if(!M)
|
||||
M = tgui_input_list(usr, "Choose a mob to play the sound to. Only they will hear it.", "Play Mob Sound", sortNames(player_list))
|
||||
if(!M || QDELETED(M))
|
||||
return
|
||||
log_admin("[key_name(src)] played a direct mob sound [S] to [M].")
|
||||
message_admins("[key_name_admin(src)] played a direct mob sound [S] to [ADMIN_LOOKUPFLW(M)].")
|
||||
SEND_SOUND(M, S)
|
||||
feedback_add_details("admin_verb", "Play Direct Mob Sound")
|
||||
|
||||
/client/proc/play_z_sound(S as sound)
|
||||
set category = "Fun"
|
||||
set name = "Play Z Sound"
|
||||
if(!check_rights(R_SOUNDS)) return
|
||||
var/target_z = mob.z
|
||||
var/sound/uploaded_sound = sound(S, repeat = 0, wait = 1, channel = 777)
|
||||
uploaded_sound.priority = 250
|
||||
|
||||
sounds_cache += S
|
||||
|
||||
if(tgui_alert(usr, "Do you ready?\nSong: [S]\nNow you can also play this sound using \"Play Server Sound\".", "Confirmation request", list("Play","Cancel")) == "Cancel")
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] played sound [S] on Z[target_z]")
|
||||
message_admins("[key_name_admin(src)] played sound [S] on Z[target_z]", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.is_preference_enabled(/datum/client_preference/play_admin_midis) && M.z == target_z)
|
||||
M << uploaded_sound
|
||||
|
||||
feedback_add_details("admin_verb", "Play Z Sound") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
|
||||
/client/proc/play_server_sound()
|
||||
set category = "Fun"
|
||||
set name = "Play Server Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
var/list/sounds = file2list("sound/serversound_list.txt");
|
||||
sounds += "--CANCEL--"
|
||||
sounds += sounds_cache
|
||||
|
||||
var/melody = tgui_input_list(usr, "Select a sound from the server to play", "Server sound list", sounds, "--CANCEL--")
|
||||
|
||||
if(melody == "--CANCEL--")
|
||||
return
|
||||
|
||||
play_sound(melody)
|
||||
feedback_add_details("admin_verb", "Play Server Sound") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
///Takes an input from either proc/play_web_sound or the request manager and runs it through youtube-dl and prompts the user before playing it to the server.
|
||||
/proc/web_sound(mob/user, input, credit)
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
var/ytdl = config.invoke_youtubedl
|
||||
if(!ytdl)
|
||||
to_chat(user, "<span class='boldwarning'>Youtube-dl was not configured, action unavailable</span>", confidential = TRUE) //Check config.txt for the INVOKE_YOUTUBEDL value
|
||||
return
|
||||
var/web_sound_url = ""
|
||||
var/stop_web_sounds = FALSE
|
||||
var/list/music_extra_data = list()
|
||||
var/duration = 0
|
||||
if(istext(input))
|
||||
var/shell_scrubbed_input = shell_url_scrub(input)
|
||||
var/list/output = world.shelleo("[ytdl] --geo-bypass --format \"bestaudio\[ext=mp3]/best\[ext=mp4]\[height <= 360]/bestaudio\[ext=m4a]/bestaudio\[ext=aac]\" --dump-single-json --no-playlist -- \"[shell_scrubbed_input]\"")
|
||||
var/errorlevel = output[SHELLEO_ERRORLEVEL]
|
||||
var/stdout = output[SHELLEO_STDOUT]
|
||||
var/stderr = output[SHELLEO_STDERR]
|
||||
if(errorlevel)
|
||||
to_chat(user, "<span class='boldwarning'>Youtube-dl URL retrieval FAILED:</span>", confidential = TRUE)
|
||||
to_chat(user, "<span class='warning'>[stderr]</span>", confidential = TRUE)
|
||||
return
|
||||
var/list/data
|
||||
try
|
||||
data = json_decode(stdout)
|
||||
catch(var/exception/e)
|
||||
to_chat(user, "<span class='boldwarning'>Youtube-dl JSON parsing FAILED:</span>", confidential = TRUE)
|
||||
to_chat(user, "<span class='warning'>[e]: [stdout]</span>", confidential = TRUE)
|
||||
return
|
||||
if (data["url"])
|
||||
web_sound_url = data["url"]
|
||||
var/title = "[data["title"]]"
|
||||
var/webpage_url = title
|
||||
if (data["webpage_url"])
|
||||
webpage_url = "<a href=\"[data["webpage_url"]]\">[title]</a>"
|
||||
music_extra_data["duration"] = DisplayTimeText(data["duration"] * 1 SECONDS)
|
||||
music_extra_data["link"] = data["webpage_url"]
|
||||
music_extra_data["artist"] = data["artist"]
|
||||
music_extra_data["upload_date"] = data["upload_date"]
|
||||
music_extra_data["album"] = data["album"]
|
||||
duration = data["duration"] * 1 SECONDS
|
||||
if (duration > 10 MINUTES)
|
||||
if((tgui_alert(user, "This song is over 10 minutes long. Are you sure you want to play it?", "Length Warning!", list("No", "Yes", "Cancel")) != "Yes"))
|
||||
return
|
||||
var/res = tgui_alert(user, "Show the title of and link to this song to the players?\n[title]", "Show Info?", list("Yes", "No", "Cancel"))
|
||||
switch(res)
|
||||
if("Yes")
|
||||
music_extra_data["title"] = data["title"]
|
||||
if("No")
|
||||
music_extra_data["link"] = "Song Link Hidden"
|
||||
music_extra_data["title"] = "Song Title Hidden"
|
||||
music_extra_data["artist"] = "Song Artist Hidden"
|
||||
music_extra_data["upload_date"] = "Song Upload Date Hidden"
|
||||
music_extra_data["album"] = "Song Album Hidden"
|
||||
if("Cancel", null)
|
||||
return
|
||||
var/anon = tgui_alert(user, "Display who played the song?", "Credit Yourself?", list("Yes", "No", "Cancel"))
|
||||
switch(anon)
|
||||
if("Yes")
|
||||
if(res == "Yes")
|
||||
to_chat(world, "<span class='boldannounce'>[user.key] played: [webpage_url]</span>", confidential = TRUE)
|
||||
else
|
||||
to_chat(world, "<span class='boldannounce'>[user.key] played a sound</span>", confidential = TRUE)
|
||||
if("No")
|
||||
if(res == "Yes")
|
||||
to_chat(world, "<span class='boldannounce'>An admin played: [webpage_url]</span>", confidential = TRUE)
|
||||
if("Cancel", null)
|
||||
return
|
||||
if(credit)
|
||||
to_chat(world, "<span class='boldannounce'>[credit]</span>", confidential = TRUE)
|
||||
//SSblackbox.record_feedback("nested tally", "played_url", 1, list("[user.ckey]", "[input]"))
|
||||
log_admin("[key_name(user)] played web sound: [input]")
|
||||
message_admins("[key_name(user)] played web sound: [input]")
|
||||
else
|
||||
//pressed ok with blank
|
||||
log_admin("[key_name(user)] stopped web sounds.")
|
||||
|
||||
message_admins("[key_name(user)] stopped web sounds.")
|
||||
web_sound_url = null
|
||||
stop_web_sounds = TRUE
|
||||
if(web_sound_url && !findtext(web_sound_url, GLOB.is_http_protocol))
|
||||
tgui_alert(user, "The media provider returned a content URL that isn't using the HTTP or HTTPS protocol. This is a security risk and the sound will not be played.", "Security Risk", list("OK"))
|
||||
to_chat(user, "<span class='boldwarning'>BLOCKED: Content URL not using HTTP(S) Protocol!</span>", confidential = TRUE)
|
||||
|
||||
return
|
||||
if(web_sound_url || stop_web_sounds)
|
||||
for(var/m in player_list)
|
||||
var/mob/M = m
|
||||
var/client/C = M.client
|
||||
if(C.is_preference_enabled(/datum/client_preference/play_admin_midis))
|
||||
if(!stop_web_sounds)
|
||||
C.tgui_panel?.play_music(web_sound_url, music_extra_data)
|
||||
else
|
||||
C.tgui_panel?.stop_music()
|
||||
|
||||
S_TIMER_COOLDOWN_START(SStimer, COOLDOWN_INTERNET_SOUND, duration)
|
||||
|
||||
feedback_add_details("admin_verb", "Play Internet Sound")
|
||||
|
||||
/client/proc/play_web_sound()
|
||||
set category = "Fun"
|
||||
set name = "Play Internet Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
var/ytdl = config.invoke_youtubedl
|
||||
if(!ytdl)
|
||||
to_chat(src, "<span class='boldwarning'>Youtube-dl was not configured, action unavailable</span>", confidential = TRUE) //Check config.txt for the INVOKE_YOUTUBEDL value
|
||||
return
|
||||
|
||||
if(S_TIMER_COOLDOWN_TIMELEFT(SStimer, COOLDOWN_INTERNET_SOUND))
|
||||
if(tgui_alert(usr, "Someone else is already playing an Internet sound! It has [DisplayTimeText(S_TIMER_COOLDOWN_TIMELEFT(SStimer, COOLDOWN_INTERNET_SOUND), 1)] remaining. \
|
||||
Would you like to override?", "Musicalis Interruptus", list("No","Yes")) != "Yes")
|
||||
return
|
||||
|
||||
var/web_sound_input = tgui_input_text(usr, "Enter content URL (supported sites only, leave blank to stop playing)", "Play Internet Sound", null)
|
||||
|
||||
if(length(web_sound_input))
|
||||
web_sound_input = trim(web_sound_input)
|
||||
if(findtext(web_sound_input, ":") && !findtext(web_sound_input, GLOB.is_http_protocol))
|
||||
to_chat(src, "<span class='boldwarning'>Non-http(s) URIs are not allowed.</span>", confidential = TRUE)
|
||||
to_chat(src, "<span class='warning'>For youtube-dl shortcuts like ytsearch: please use the appropriate full URL from the website.</span>", confidential = TRUE)
|
||||
return
|
||||
web_sound(usr, web_sound_input)
|
||||
else
|
||||
web_sound(usr, null)
|
||||
|
||||
/client/proc/stop_sounds()
|
||||
set category = "Debug"
|
||||
set name = "Stop All Playing Sounds"
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] stopped all currently playing sounds.")
|
||||
message_admins("[key_name_admin(src)] stopped all currently playing sounds.")
|
||||
for(var/mob/M in player_list)
|
||||
SEND_SOUND(M, sound(null))
|
||||
var/client/C = M.client
|
||||
C?.tgui_panel?.stop_music()
|
||||
|
||||
S_TIMER_COOLDOWN_RESET(SStimer, COOLDOWN_INTERNET_SOUND)
|
||||
feedback_add_details("admin_verb", "Stop All Playing Sounds")
|
||||
|
||||
//world/proc/shelleo
|
||||
#undef SHELLEO_ERRORLEVEL
|
||||
#undef SHELLEO_STDOUT
|
||||
#undef SHELLEO_STDERR
|
||||
|
||||
/*
|
||||
/client/proc/cuban_pete()
|
||||
set category = "Fun"
|
||||
set name = "Cuban Pete Time"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has declared Cuban Pete Time!", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'cubanpetetime.ogg'
|
||||
|
||||
for(var/mob/living/carbon/human/CP in human_mob_list)
|
||||
if(CP.real_name=="Cuban Pete" && CP.key!="Rosham")
|
||||
to_chat(CP, "Your body can't contain the rhumba beat")
|
||||
CP.gib()
|
||||
|
||||
|
||||
/client/proc/bananaphone()
|
||||
set category = "Fun"
|
||||
set name = "Banana Phone"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has activated Banana Phone!", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'bananaphone.ogg'
|
||||
|
||||
|
||||
/client/proc/space_asshole()
|
||||
set category = "Fun"
|
||||
set name = "Space Asshole"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has played the Space Asshole Hymn.", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'sound/music/space_asshole.ogg'
|
||||
|
||||
|
||||
/client/proc/honk_theme()
|
||||
set category = "Fun"
|
||||
set name = "Honk"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has creeped everyone out with Blackest Honks.", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'honk_theme.ogg'*/
|
||||
//world/proc/shelleo
|
||||
#define SHELLEO_ERRORLEVEL 1
|
||||
#define SHELLEO_STDOUT 2
|
||||
#define SHELLEO_STDERR 3
|
||||
|
||||
var/list/sounds_cache = list()
|
||||
|
||||
/client/proc/play_sound(S as sound)
|
||||
set category = "Fun"
|
||||
set name = "Play Global Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
var/freq = 1
|
||||
var/vol = tgui_input_number(usr, "What volume would you like the sound to play at?",, 100, 100, 1)
|
||||
if(!vol)
|
||||
return
|
||||
vol = clamp(vol, 1, 100)
|
||||
|
||||
var/sound/admin_sound = new()
|
||||
admin_sound.file = S
|
||||
admin_sound.priority = 250
|
||||
admin_sound.channel = 777
|
||||
admin_sound.frequency = freq
|
||||
admin_sound.wait = 1
|
||||
admin_sound.repeat = FALSE
|
||||
admin_sound.status = SOUND_STREAM
|
||||
admin_sound.volume = vol
|
||||
|
||||
sounds_cache += S
|
||||
|
||||
var/res = tgui_alert(usr, "Show the title of this song ([S]) to the players?\nOptions 'Yes' and 'No' will play the sound.",, list("Yes", "No", "Cancel"))
|
||||
switch(res)
|
||||
if("Yes")
|
||||
to_chat(world, "<span class='boldannounce'>An admin played: [S]</span>", confidential = TRUE)
|
||||
if("Cancel")
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] played sound [S]")
|
||||
message_admins("[key_name_admin(src)] played sound [S]", 1)
|
||||
|
||||
for(var/mob/M in player_list)
|
||||
if(M.is_preference_enabled(/datum/client_preference/play_admin_midis))
|
||||
admin_sound.volume = vol * M.client.admin_music_volume
|
||||
SEND_SOUND(M, admin_sound)
|
||||
admin_sound.volume = vol
|
||||
|
||||
feedback_add_details("admin_verb", "Play Global Sound")
|
||||
|
||||
/client/proc/play_local_sound(S as sound)
|
||||
set category = "Fun"
|
||||
set name = "Play Local Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] played a local sound [S]")
|
||||
message_admins("[key_name_admin(src)] played a local sound [S]", 1)
|
||||
playsound(src.mob, S, 50, 0, 0)
|
||||
feedback_add_details("admin_verb", "Play Local Sound")
|
||||
|
||||
/client/proc/play_direct_mob_sound(S as sound, mob/M)
|
||||
set category = "Fun"
|
||||
set name = "Play Direct Mob Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
if(!M)
|
||||
M = tgui_input_list(usr, "Choose a mob to play the sound to. Only they will hear it.", "Play Mob Sound", sortNames(player_list))
|
||||
if(!M || QDELETED(M))
|
||||
return
|
||||
log_admin("[key_name(src)] played a direct mob sound [S] to [M].")
|
||||
message_admins("[key_name_admin(src)] played a direct mob sound [S] to [ADMIN_LOOKUPFLW(M)].")
|
||||
SEND_SOUND(M, S)
|
||||
feedback_add_details("admin_verb", "Play Direct Mob Sound")
|
||||
|
||||
/client/proc/play_z_sound(S as sound)
|
||||
set category = "Fun"
|
||||
set name = "Play Z Sound"
|
||||
if(!check_rights(R_SOUNDS)) return
|
||||
var/target_z = mob.z
|
||||
var/sound/uploaded_sound = sound(S, repeat = 0, wait = 1, channel = 777)
|
||||
uploaded_sound.priority = 250
|
||||
|
||||
sounds_cache += S
|
||||
|
||||
if(tgui_alert(usr, "Do you ready?\nSong: [S]\nNow you can also play this sound using \"Play Server Sound\".", "Confirmation request", list("Play","Cancel")) == "Cancel")
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] played sound [S] on Z[target_z]")
|
||||
message_admins("[key_name_admin(src)] played sound [S] on Z[target_z]", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.is_preference_enabled(/datum/client_preference/play_admin_midis) && M.z == target_z)
|
||||
M << uploaded_sound
|
||||
|
||||
feedback_add_details("admin_verb", "Play Z Sound") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
|
||||
/client/proc/play_server_sound()
|
||||
set category = "Fun"
|
||||
set name = "Play Server Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
var/list/sounds = file2list("sound/serversound_list.txt");
|
||||
sounds += "--CANCEL--"
|
||||
sounds += sounds_cache
|
||||
|
||||
var/melody = tgui_input_list(usr, "Select a sound from the server to play", "Server sound list", sounds, "--CANCEL--")
|
||||
|
||||
if(melody == "--CANCEL--")
|
||||
return
|
||||
|
||||
play_sound(melody)
|
||||
feedback_add_details("admin_verb", "Play Server Sound") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
///Takes an input from either proc/play_web_sound or the request manager and runs it through youtube-dl and prompts the user before playing it to the server.
|
||||
/proc/web_sound(mob/user, input, credit)
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
var/ytdl = config.invoke_youtubedl
|
||||
if(!ytdl)
|
||||
to_chat(user, "<span class='boldwarning'>Youtube-dl was not configured, action unavailable</span>", confidential = TRUE) //Check config.txt for the INVOKE_YOUTUBEDL value
|
||||
return
|
||||
var/web_sound_url = ""
|
||||
var/stop_web_sounds = FALSE
|
||||
var/list/music_extra_data = list()
|
||||
var/duration = 0
|
||||
if(istext(input))
|
||||
var/shell_scrubbed_input = shell_url_scrub(input)
|
||||
var/list/output = world.shelleo("[ytdl] --geo-bypass --format \"bestaudio\[ext=mp3]/best\[ext=mp4]\[height <= 360]/bestaudio\[ext=m4a]/bestaudio\[ext=aac]\" --dump-single-json --no-playlist -- \"[shell_scrubbed_input]\"")
|
||||
var/errorlevel = output[SHELLEO_ERRORLEVEL]
|
||||
var/stdout = output[SHELLEO_STDOUT]
|
||||
var/stderr = output[SHELLEO_STDERR]
|
||||
if(errorlevel)
|
||||
to_chat(user, "<span class='boldwarning'>Youtube-dl URL retrieval FAILED:</span>", confidential = TRUE)
|
||||
to_chat(user, "<span class='warning'>[stderr]</span>", confidential = TRUE)
|
||||
return
|
||||
var/list/data
|
||||
try
|
||||
data = json_decode(stdout)
|
||||
catch(var/exception/e)
|
||||
to_chat(user, "<span class='boldwarning'>Youtube-dl JSON parsing FAILED:</span>", confidential = TRUE)
|
||||
to_chat(user, "<span class='warning'>[e]: [stdout]</span>", confidential = TRUE)
|
||||
return
|
||||
if (data["url"])
|
||||
web_sound_url = data["url"]
|
||||
var/title = "[data["title"]]"
|
||||
var/webpage_url = title
|
||||
if (data["webpage_url"])
|
||||
webpage_url = "<a href=\"[data["webpage_url"]]\">[title]</a>"
|
||||
music_extra_data["duration"] = DisplayTimeText(data["duration"] * 1 SECONDS)
|
||||
music_extra_data["link"] = data["webpage_url"]
|
||||
music_extra_data["artist"] = data["artist"]
|
||||
music_extra_data["upload_date"] = data["upload_date"]
|
||||
music_extra_data["album"] = data["album"]
|
||||
duration = data["duration"] * 1 SECONDS
|
||||
if (duration > 10 MINUTES)
|
||||
if((tgui_alert(user, "This song is over 10 minutes long. Are you sure you want to play it?", "Length Warning!", list("No", "Yes", "Cancel")) != "Yes"))
|
||||
return
|
||||
var/res = tgui_alert(user, "Show the title of and link to this song to the players?\n[title]", "Show Info?", list("Yes", "No", "Cancel"))
|
||||
switch(res)
|
||||
if("Yes")
|
||||
music_extra_data["title"] = data["title"]
|
||||
if("No")
|
||||
music_extra_data["link"] = "Song Link Hidden"
|
||||
music_extra_data["title"] = "Song Title Hidden"
|
||||
music_extra_data["artist"] = "Song Artist Hidden"
|
||||
music_extra_data["upload_date"] = "Song Upload Date Hidden"
|
||||
music_extra_data["album"] = "Song Album Hidden"
|
||||
if("Cancel", null)
|
||||
return
|
||||
var/anon = tgui_alert(user, "Display who played the song?", "Credit Yourself?", list("Yes", "No", "Cancel"))
|
||||
switch(anon)
|
||||
if("Yes")
|
||||
if(res == "Yes")
|
||||
to_chat(world, "<span class='boldannounce'>[user.key] played: [webpage_url]</span>", confidential = TRUE)
|
||||
else
|
||||
to_chat(world, "<span class='boldannounce'>[user.key] played a sound</span>", confidential = TRUE)
|
||||
if("No")
|
||||
if(res == "Yes")
|
||||
to_chat(world, "<span class='boldannounce'>An admin played: [webpage_url]</span>", confidential = TRUE)
|
||||
if("Cancel", null)
|
||||
return
|
||||
if(credit)
|
||||
to_chat(world, "<span class='boldannounce'>[credit]</span>", confidential = TRUE)
|
||||
//SSblackbox.record_feedback("nested tally", "played_url", 1, list("[user.ckey]", "[input]"))
|
||||
log_admin("[key_name(user)] played web sound: [input]")
|
||||
message_admins("[key_name(user)] played web sound: [input]")
|
||||
else
|
||||
//pressed ok with blank
|
||||
log_admin("[key_name(user)] stopped web sounds.")
|
||||
|
||||
message_admins("[key_name(user)] stopped web sounds.")
|
||||
web_sound_url = null
|
||||
stop_web_sounds = TRUE
|
||||
if(web_sound_url && !findtext(web_sound_url, GLOB.is_http_protocol))
|
||||
tgui_alert(user, "The media provider returned a content URL that isn't using the HTTP or HTTPS protocol. This is a security risk and the sound will not be played.", "Security Risk", list("OK"))
|
||||
to_chat(user, "<span class='boldwarning'>BLOCKED: Content URL not using HTTP(S) Protocol!</span>", confidential = TRUE)
|
||||
|
||||
return
|
||||
if(web_sound_url || stop_web_sounds)
|
||||
for(var/m in player_list)
|
||||
var/mob/M = m
|
||||
var/client/C = M.client
|
||||
if(C.is_preference_enabled(/datum/client_preference/play_admin_midis))
|
||||
if(!stop_web_sounds)
|
||||
C.tgui_panel?.play_music(web_sound_url, music_extra_data)
|
||||
else
|
||||
C.tgui_panel?.stop_music()
|
||||
|
||||
S_TIMER_COOLDOWN_START(SStimer, COOLDOWN_INTERNET_SOUND, duration)
|
||||
|
||||
feedback_add_details("admin_verb", "Play Internet Sound")
|
||||
|
||||
/client/proc/play_web_sound()
|
||||
set category = "Fun"
|
||||
set name = "Play Internet Sound"
|
||||
if(!check_rights(R_SOUNDS))
|
||||
return
|
||||
|
||||
var/ytdl = config.invoke_youtubedl
|
||||
if(!ytdl)
|
||||
to_chat(src, "<span class='boldwarning'>Youtube-dl was not configured, action unavailable</span>", confidential = TRUE) //Check config.txt for the INVOKE_YOUTUBEDL value
|
||||
return
|
||||
|
||||
if(S_TIMER_COOLDOWN_TIMELEFT(SStimer, COOLDOWN_INTERNET_SOUND))
|
||||
if(tgui_alert(usr, "Someone else is already playing an Internet sound! It has [DisplayTimeText(S_TIMER_COOLDOWN_TIMELEFT(SStimer, COOLDOWN_INTERNET_SOUND), 1)] remaining. \
|
||||
Would you like to override?", "Musicalis Interruptus", list("No","Yes")) != "Yes")
|
||||
return
|
||||
|
||||
var/web_sound_input = tgui_input_text(usr, "Enter content URL (supported sites only, leave blank to stop playing)", "Play Internet Sound", null)
|
||||
|
||||
if(length(web_sound_input))
|
||||
web_sound_input = trim(web_sound_input)
|
||||
if(findtext(web_sound_input, ":") && !findtext(web_sound_input, GLOB.is_http_protocol))
|
||||
to_chat(src, "<span class='boldwarning'>Non-http(s) URIs are not allowed.</span>", confidential = TRUE)
|
||||
to_chat(src, "<span class='warning'>For youtube-dl shortcuts like ytsearch: please use the appropriate full URL from the website.</span>", confidential = TRUE)
|
||||
return
|
||||
web_sound(usr, web_sound_input)
|
||||
else
|
||||
web_sound(usr, null)
|
||||
|
||||
/client/proc/stop_sounds()
|
||||
set category = "Debug"
|
||||
set name = "Stop All Playing Sounds"
|
||||
if(!src.holder)
|
||||
return
|
||||
|
||||
log_admin("[key_name(src)] stopped all currently playing sounds.")
|
||||
message_admins("[key_name_admin(src)] stopped all currently playing sounds.")
|
||||
for(var/mob/M in player_list)
|
||||
SEND_SOUND(M, sound(null))
|
||||
var/client/C = M.client
|
||||
C?.tgui_panel?.stop_music()
|
||||
|
||||
S_TIMER_COOLDOWN_RESET(SStimer, COOLDOWN_INTERNET_SOUND)
|
||||
feedback_add_details("admin_verb", "Stop All Playing Sounds")
|
||||
|
||||
//world/proc/shelleo
|
||||
#undef SHELLEO_ERRORLEVEL
|
||||
#undef SHELLEO_STDOUT
|
||||
#undef SHELLEO_STDERR
|
||||
|
||||
/*
|
||||
/client/proc/cuban_pete()
|
||||
set category = "Fun"
|
||||
set name = "Cuban Pete Time"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has declared Cuban Pete Time!", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'cubanpetetime.ogg'
|
||||
|
||||
for(var/mob/living/carbon/human/CP in human_mob_list)
|
||||
if(CP.real_name=="Cuban Pete" && CP.key!="Rosham")
|
||||
to_chat(CP, "Your body can't contain the rhumba beat")
|
||||
CP.gib()
|
||||
|
||||
|
||||
/client/proc/bananaphone()
|
||||
set category = "Fun"
|
||||
set name = "Banana Phone"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has activated Banana Phone!", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'bananaphone.ogg'
|
||||
|
||||
|
||||
/client/proc/space_asshole()
|
||||
set category = "Fun"
|
||||
set name = "Space Asshole"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has played the Space Asshole Hymn.", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'sound/music/space_asshole.ogg'
|
||||
|
||||
|
||||
/client/proc/honk_theme()
|
||||
set category = "Fun"
|
||||
set name = "Honk"
|
||||
|
||||
message_admins("[key_name_admin(usr)] has creeped everyone out with Blackest Honks.", 1)
|
||||
for(var/mob/M in player_list)
|
||||
if(M.client)
|
||||
if(M.client.midis)
|
||||
M << 'honk_theme.ogg'*/
|
||||
|
||||
@@ -1,44 +1,44 @@
|
||||
/mob/verb/pray()
|
||||
set category = "IC"
|
||||
set name = "Pray"
|
||||
|
||||
if(say_disabled) //This is here to try to identify lag problems
|
||||
to_chat(usr, span_red("Speech is currently admin-disabled."))
|
||||
return
|
||||
|
||||
var/raw_msg = sanitize(tgui_input_text(usr, "Prayers are sent to staff but do not open tickets or go to Discord. If you have a technical difficulty or an event/spice idea/hook - please ahelp instead. Thank you!", "Pray", null, MAX_MESSAGE_LEN))
|
||||
if(!raw_msg) return
|
||||
|
||||
if(usr.client)
|
||||
if(raw_msg)
|
||||
client.handle_spam_prevention(MUTE_PRAY)
|
||||
if(usr.client.prefs.muted & MUTE_PRAY)
|
||||
to_chat(usr, span_red("You cannot pray (muted)."))
|
||||
return
|
||||
|
||||
var/icon/cross = icon('icons/obj/storage.dmi',"bible")
|
||||
var/msg = "<span class='filter_pray'>" + span_blue("\icon[cross][bicon(cross)] <b>" + span_purple("PRAY: ") + "[key_name(src, 1)] [ADMIN_QUE(src)] [ADMIN_PP(src)] [ADMIN_VV(src)] [ADMIN_SM(src)] ([admin_jump_link(src, src)]) [ADMIN_CA(src)] [ADMIN_SC(src)] [ADMIN_SMITE(src)]:</b> [raw_msg]") + "</span>"
|
||||
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(R_ADMIN|R_EVENT & C.holder.rights)
|
||||
if(C.is_preference_enabled(/datum/client_preference/admin/show_chat_prayers))
|
||||
to_chat(C, msg, type = MESSAGE_TYPE_PRAYER, confidential = TRUE)
|
||||
C << 'sound/effects/ding.ogg'
|
||||
to_chat(usr, "Your prayers have been received by the gods.", confidential = TRUE)
|
||||
|
||||
feedback_add_details("admin_verb","PR") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
log_pray(raw_msg, src)
|
||||
|
||||
/proc/CentCom_announce(var/msg, var/mob/Sender, var/iamessage)
|
||||
msg = span_blue("<b>" + span_orange("[uppertext(using_map.boss_short)]M[iamessage ? " IA" : ""]:") + "[key_name(Sender, 1)] [ADMIN_PP(Sender)] [ADMIN_VV(Sender)] [ADMIN_SM(Sender)] ([admin_jump_link(Sender)]) [ADMIN_CA(Sender)] [ADMIN_BSA(Sender)] [ADMIN_CENTCOM_REPLY(Sender)]:</b> [msg]")
|
||||
for(var/client/C in GLOB.admins) //VOREStation Edit - GLOB admins
|
||||
if(R_ADMIN|R_EVENT & C.holder.rights)
|
||||
to_chat(C,msg)
|
||||
C << 'sound/machines/signal.ogg'
|
||||
|
||||
/proc/Syndicate_announce(var/msg, var/mob/Sender)
|
||||
msg = span_blue("<b>" + span_crimson("ILLEGAL:") + "[key_name(Sender, 1)] [ADMIN_PP(Sender)] [ADMIN_VV(Sender)] [ADMIN_SM(Sender)] ([admin_jump_link(Sender)]) [ADMIN_CA(Sender)] [ADMIN_BSA(Sender)] [ADMIN_SYNDICATE_REPLY(Sender)]:</b> [msg]")
|
||||
for(var/client/C in GLOB.admins) //VOREStation Edit - GLOB admins
|
||||
if(R_ADMIN|R_EVENT & C.holder.rights)
|
||||
to_chat(C,msg)
|
||||
C << 'sound/machines/signal.ogg'
|
||||
/mob/verb/pray()
|
||||
set category = "IC"
|
||||
set name = "Pray"
|
||||
|
||||
if(say_disabled) //This is here to try to identify lag problems
|
||||
to_chat(usr, span_red("Speech is currently admin-disabled."))
|
||||
return
|
||||
|
||||
var/raw_msg = sanitize(tgui_input_text(usr, "Prayers are sent to staff but do not open tickets or go to Discord. If you have a technical difficulty or an event/spice idea/hook - please ahelp instead. Thank you!", "Pray", null, MAX_MESSAGE_LEN))
|
||||
if(!raw_msg) return
|
||||
|
||||
if(usr.client)
|
||||
if(raw_msg)
|
||||
client.handle_spam_prevention(MUTE_PRAY)
|
||||
if(usr.client.prefs.muted & MUTE_PRAY)
|
||||
to_chat(usr, span_red("You cannot pray (muted)."))
|
||||
return
|
||||
|
||||
var/icon/cross = icon('icons/obj/storage.dmi',"bible")
|
||||
var/msg = "<span class='filter_pray'>" + span_blue("\icon[cross][bicon(cross)] <b>" + span_purple("PRAY: ") + "[key_name(src, 1)] [ADMIN_QUE(src)] [ADMIN_PP(src)] [ADMIN_VV(src)] [ADMIN_SM(src)] ([admin_jump_link(src, src)]) [ADMIN_CA(src)] [ADMIN_SC(src)] [ADMIN_SMITE(src)]:</b> [raw_msg]") + "</span>"
|
||||
|
||||
for(var/client/C in GLOB.admins)
|
||||
if(R_ADMIN|R_EVENT & C.holder.rights)
|
||||
if(C.is_preference_enabled(/datum/client_preference/admin/show_chat_prayers))
|
||||
to_chat(C, msg, type = MESSAGE_TYPE_PRAYER, confidential = TRUE)
|
||||
C << 'sound/effects/ding.ogg'
|
||||
to_chat(usr, "Your prayers have been received by the gods.", confidential = TRUE)
|
||||
|
||||
feedback_add_details("admin_verb","PR") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
log_pray(raw_msg, src)
|
||||
|
||||
/proc/CentCom_announce(var/msg, var/mob/Sender, var/iamessage)
|
||||
msg = span_blue("<b>" + span_orange("[uppertext(using_map.boss_short)]M[iamessage ? " IA" : ""]:") + "[key_name(Sender, 1)] [ADMIN_PP(Sender)] [ADMIN_VV(Sender)] [ADMIN_SM(Sender)] ([admin_jump_link(Sender)]) [ADMIN_CA(Sender)] [ADMIN_BSA(Sender)] [ADMIN_CENTCOM_REPLY(Sender)]:</b> [msg]")
|
||||
for(var/client/C in GLOB.admins) //VOREStation Edit - GLOB admins
|
||||
if(R_ADMIN|R_EVENT & C.holder.rights)
|
||||
to_chat(C,msg)
|
||||
C << 'sound/machines/signal.ogg'
|
||||
|
||||
/proc/Syndicate_announce(var/msg, var/mob/Sender)
|
||||
msg = span_blue("<b>" + span_crimson("ILLEGAL:") + "[key_name(Sender, 1)] [ADMIN_PP(Sender)] [ADMIN_VV(Sender)] [ADMIN_SM(Sender)] ([admin_jump_link(Sender)]) [ADMIN_CA(Sender)] [ADMIN_BSA(Sender)] [ADMIN_SYNDICATE_REPLY(Sender)]:</b> [msg]")
|
||||
for(var/client/C in GLOB.admins) //VOREStation Edit - GLOB admins
|
||||
if(R_ADMIN|R_EVENT & C.holder.rights)
|
||||
to_chat(C,msg)
|
||||
C << 'sound/machines/signal.ogg'
|
||||
|
||||
+1164
-1164
File diff suppressed because it is too large
Load Diff
@@ -1,56 +1,56 @@
|
||||
//STRIKE TEAMS
|
||||
var/const/commandos_possible = 6 //if more Commandos are needed in the future
|
||||
|
||||
/client/proc/strike_team()
|
||||
set category = "Fun"
|
||||
set name = "Spawn Strike Team"
|
||||
set desc = "Spawns a strike team if you want to run an admin event."
|
||||
|
||||
if(!src.holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
|
||||
if(!ticker)
|
||||
to_chat(usr, span_red("The game hasn't started yet!"))
|
||||
return
|
||||
|
||||
if(world.time < 6000)
|
||||
to_chat(usr, span_red("There are [(6000-world.time)/10] seconds remaining before it may be called."))
|
||||
return
|
||||
|
||||
var/datum/antagonist/deathsquad/team
|
||||
|
||||
var/choice = tgui_input_list(usr, "Select type of strike team:", "Strike Team", list("Heavy Asset Protection", "Mercenaries"))
|
||||
if(!choice)
|
||||
return
|
||||
|
||||
switch(choice)
|
||||
if("Heavy Asset Protection")
|
||||
team = deathsquad
|
||||
if("Mercenaries")
|
||||
team = commandos
|
||||
else
|
||||
return
|
||||
|
||||
if(team.deployed)
|
||||
to_chat(usr, span_red("Someone is already sending a team."))
|
||||
return
|
||||
|
||||
if(tgui_alert(usr, "Do you want to send in a strike team? Once enabled, this is irreversible.","Strike Team",list("Yes","No"))!="Yes")
|
||||
return
|
||||
|
||||
tgui_alert(usr, "This 'mode' will go on until everyone is dead or the station is destroyed. You may also admin-call the evac shuttle when appropriate. Spawned commandos have internals cameras which are viewable through a monitor inside the Spec. Ops. Office. Assigning the team's detailed task is recommended from there. While you will be able to manually pick the candidates from active ghosts, their assignment in the squad will be random.") // Should remain tgui_alert() (blocking)
|
||||
|
||||
choice = null
|
||||
while(!choice)
|
||||
choice = sanitize(tgui_input_text(src, "Please specify which mission the strike team shall undertake.", "Specify Mission", ""))
|
||||
if(!choice)
|
||||
if(tgui_alert(usr, "Error, no mission set. Do you want to exit the setup process?","Strike Team",list("Yes","No"))=="Yes")
|
||||
return
|
||||
consider_ert_load() //VOREStation Add
|
||||
|
||||
if(team.deployed)
|
||||
to_chat(usr, "Looks like someone beat you to it.")
|
||||
return
|
||||
|
||||
team.attempt_random_spawn()
|
||||
//STRIKE TEAMS
|
||||
var/const/commandos_possible = 6 //if more Commandos are needed in the future
|
||||
|
||||
/client/proc/strike_team()
|
||||
set category = "Fun"
|
||||
set name = "Spawn Strike Team"
|
||||
set desc = "Spawns a strike team if you want to run an admin event."
|
||||
|
||||
if(!src.holder)
|
||||
to_chat(src, "Only administrators may use this command.")
|
||||
return
|
||||
|
||||
if(!ticker)
|
||||
to_chat(usr, span_red("The game hasn't started yet!"))
|
||||
return
|
||||
|
||||
if(world.time < 6000)
|
||||
to_chat(usr, span_red("There are [(6000-world.time)/10] seconds remaining before it may be called."))
|
||||
return
|
||||
|
||||
var/datum/antagonist/deathsquad/team
|
||||
|
||||
var/choice = tgui_input_list(usr, "Select type of strike team:", "Strike Team", list("Heavy Asset Protection", "Mercenaries"))
|
||||
if(!choice)
|
||||
return
|
||||
|
||||
switch(choice)
|
||||
if("Heavy Asset Protection")
|
||||
team = deathsquad
|
||||
if("Mercenaries")
|
||||
team = commandos
|
||||
else
|
||||
return
|
||||
|
||||
if(team.deployed)
|
||||
to_chat(usr, span_red("Someone is already sending a team."))
|
||||
return
|
||||
|
||||
if(tgui_alert(usr, "Do you want to send in a strike team? Once enabled, this is irreversible.","Strike Team",list("Yes","No"))!="Yes")
|
||||
return
|
||||
|
||||
tgui_alert(usr, "This 'mode' will go on until everyone is dead or the station is destroyed. You may also admin-call the evac shuttle when appropriate. Spawned commandos have internals cameras which are viewable through a monitor inside the Spec. Ops. Office. Assigning the team's detailed task is recommended from there. While you will be able to manually pick the candidates from active ghosts, their assignment in the squad will be random.") // Should remain tgui_alert() (blocking)
|
||||
|
||||
choice = null
|
||||
while(!choice)
|
||||
choice = sanitize(tgui_input_text(src, "Please specify which mission the strike team shall undertake.", "Specify Mission", ""))
|
||||
if(!choice)
|
||||
if(tgui_alert(usr, "Error, no mission set. Do you want to exit the setup process?","Strike Team",list("Yes","No"))=="Yes")
|
||||
return
|
||||
consider_ert_load() //VOREStation Add
|
||||
|
||||
if(team.deployed)
|
||||
to_chat(usr, "Looks like someone beat you to it.")
|
||||
return
|
||||
|
||||
team.attempt_random_spawn()
|
||||
|
||||
@@ -1,22 +1,22 @@
|
||||
/client/proc/triple_ai()
|
||||
set category = "Fun"
|
||||
set name = "Create AI Triumvirate"
|
||||
|
||||
if(ticker.current_state > GAME_STATE_PREGAME)
|
||||
to_chat(usr, "This option is currently only usable during pregame. This may change at a later date.")
|
||||
return
|
||||
|
||||
if(job_master && ticker)
|
||||
var/datum/job/job = job_master.GetJob("AI")
|
||||
if(!job)
|
||||
to_chat(usr, "Unable to locate the AI job")
|
||||
return
|
||||
if(ticker.triai)
|
||||
ticker.triai = 0
|
||||
to_chat(usr, "Only one AI will be spawned at round start.")
|
||||
message_admins(span_blue("[key_name_admin(usr)] has toggled off triple AIs at round start."), 1)
|
||||
else
|
||||
ticker.triai = 1
|
||||
to_chat(usr, "There will be an AI Triumvirate at round start.")
|
||||
message_admins(span_blue("[key_name_admin(usr)] has toggled on triple AIs at round start."), 1)
|
||||
return
|
||||
/client/proc/triple_ai()
|
||||
set category = "Fun"
|
||||
set name = "Create AI Triumvirate"
|
||||
|
||||
if(ticker.current_state > GAME_STATE_PREGAME)
|
||||
to_chat(usr, "This option is currently only usable during pregame. This may change at a later date.")
|
||||
return
|
||||
|
||||
if(job_master && ticker)
|
||||
var/datum/job/job = job_master.GetJob("AI")
|
||||
if(!job)
|
||||
to_chat(usr, "Unable to locate the AI job")
|
||||
return
|
||||
if(ticker.triai)
|
||||
ticker.triai = 0
|
||||
to_chat(usr, "Only one AI will be spawned at round start.")
|
||||
message_admins(span_blue("[key_name_admin(usr)] has toggled off triple AIs at round start."), 1)
|
||||
else
|
||||
ticker.triai = 1
|
||||
to_chat(usr, "There will be an AI Triumvirate at round start.")
|
||||
message_admins(span_blue("[key_name_admin(usr)] has toggled on triple AIs at round start."), 1)
|
||||
return
|
||||
|
||||
@@ -97,7 +97,7 @@
|
||||
|
||||
|
||||
if (VV_NUM)
|
||||
.["value"] = tgui_input_number(usr, "Enter new number:", "Num", current_value, INFINITY, -INFINITY)
|
||||
.["value"] = tgui_input_number(usr, "Enter new number:", "Num", current_value, INFINITY, -INFINITY, round_value = FALSE)
|
||||
if (.["value"] == null)
|
||||
.["class"] = null
|
||||
return
|
||||
|
||||
@@ -1,285 +1,285 @@
|
||||
/client/proc/debug_variables(datum/D in world)
|
||||
set category = "Debug"
|
||||
set name = "View Variables"
|
||||
//set src in world
|
||||
var/static/cookieoffset = rand(1, 9999) //to force cookies to reset after the round.
|
||||
|
||||
if(!usr.client || !usr.client.holder) //The usr vs src abuse in this proc is intentional and must not be changed
|
||||
to_chat(usr, "<span class='danger'>You need to be an administrator to access this.</span>")
|
||||
return
|
||||
|
||||
if(!D)
|
||||
return
|
||||
|
||||
var/islist = islist(D)
|
||||
if (!islist && !istype(D))
|
||||
return
|
||||
|
||||
//VOREStation Edit Start - the rest of this proc in a spawn
|
||||
spawn(0)
|
||||
var/title = ""
|
||||
var/refid = "\ref[D]"
|
||||
var/icon/sprite
|
||||
var/hash
|
||||
|
||||
var/type = /list
|
||||
if (!islist)
|
||||
type = D.type
|
||||
|
||||
if(istype(D, /atom))
|
||||
var/atom/AT = D
|
||||
if(AT.icon && AT.icon_state)
|
||||
sprite = new /icon(AT.icon, AT.icon_state)
|
||||
hash = md5(AT.icon)
|
||||
hash = md5(hash + AT.icon_state)
|
||||
src << browse_rsc(sprite, "vv[hash].png")
|
||||
|
||||
title = "[D] (\ref[D]) = [type]"
|
||||
var/formatted_type = replacetext("[type]", "/", "<wbr>/")
|
||||
|
||||
var/sprite_text
|
||||
if(sprite)
|
||||
sprite_text = "<img src='vv[hash].png'></td><td>"
|
||||
var/list/header = islist(D)? list("<b>/list</b>") : D.vv_get_header()
|
||||
|
||||
var/marked
|
||||
if(holder && holder.marked_datum && holder.marked_datum == D)
|
||||
marked = VV_MSG_MARKED
|
||||
var/varedited_line = ""
|
||||
if(!islist && (D.datum_flags & DF_VAR_EDITED))
|
||||
varedited_line = VV_MSG_EDITED
|
||||
var/deleted_line
|
||||
if(!islist && D.gc_destroyed)
|
||||
deleted_line = VV_MSG_DELETED
|
||||
|
||||
var/list/dropdownoptions = list()
|
||||
var/autoconvert_dropdown = FALSE
|
||||
if (islist)
|
||||
dropdownoptions = list(
|
||||
"---",
|
||||
"Add Item" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_ADD]=TRUE;target=[refid]",
|
||||
"Remove Nulls" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_ERASE_NULLS]=TRUE;target=[refid]",
|
||||
"Remove Dupes" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_ERASE_DUPES]=TRUE;target=[refid]",
|
||||
"Set len" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_SET_LENGTH]=TRUE;target=[refid]",
|
||||
"Shuffle" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_SHUFFLE]=TRUE;target=[refid]",
|
||||
// "Show VV To Player" = "?_src_=vars;[HrefToken()];[VV_HK_EXPOSE]=TRUE;target=[refid]" // TODO - Not yet implemented for lists
|
||||
)
|
||||
autoconvert_dropdown = TRUE
|
||||
else
|
||||
dropdownoptions = D.vv_get_dropdown()
|
||||
var/list/dropdownoptions_html = list()
|
||||
if(autoconvert_dropdown)
|
||||
for (var/name in dropdownoptions)
|
||||
var/link = dropdownoptions[name]
|
||||
if (link)
|
||||
dropdownoptions_html += "<option value='[link]'>[name]</option>"
|
||||
else
|
||||
dropdownoptions_html += "<option value>[name]</option>"
|
||||
else
|
||||
dropdownoptions_html = dropdownoptions + D.get_view_variables_options()
|
||||
|
||||
var/list/names = list()
|
||||
if (!islist)
|
||||
names = D.get_variables()
|
||||
//sleep(1)//For some reason, without this sleep, VVing will cause client to disconnect on certain objects. //VOREStation edit - commented out, replaced with spawn(0) above
|
||||
|
||||
var/list/variable_html = list()
|
||||
if (islist)
|
||||
var/list/L = D
|
||||
for (var/i in 1 to L.len)
|
||||
var/key = L[i]
|
||||
var/value
|
||||
if (IS_NORMAL_LIST(L) && IS_VALID_ASSOC_KEY(key))
|
||||
value = L[key]
|
||||
variable_html += debug_variable(i, value, 0, D)
|
||||
else
|
||||
|
||||
names = sortList(names)
|
||||
for (var/V in names)
|
||||
if(D.can_vv_get(V))
|
||||
variable_html += D.vv_get_var(V)
|
||||
|
||||
var/html = {"
|
||||
<html>
|
||||
<head>
|
||||
<title>[title]</title>
|
||||
<style>
|
||||
body {
|
||||
font-family: Verdana, sans-serif;
|
||||
font-size: 9pt;
|
||||
}
|
||||
.value {
|
||||
font-family: "Courier New", monospace;
|
||||
font-size: 8pt;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body onload='selectTextField()' onkeydown='return handle_keydown()' onkeyup='handle_keyup()'>
|
||||
<script type="text/javascript">
|
||||
// onload
|
||||
function selectTextField() {
|
||||
var filter_text = document.getElementById('filter');
|
||||
filter_text.focus();
|
||||
filter_text.select();
|
||||
var lastsearch = getCookie("[refid][cookieoffset]search");
|
||||
if (lastsearch) {
|
||||
filter_text.value = lastsearch;
|
||||
updateSearch();
|
||||
}
|
||||
}
|
||||
function getCookie(cname) {
|
||||
var name = cname + "=";
|
||||
var ca = document.cookie.split(';');
|
||||
for(var i=0; i<ca.length; i++) {
|
||||
var c = ca\[i];
|
||||
while (c.charAt(0)==' ') c = c.substring(1,c.length);
|
||||
if (c.indexOf(name)==0) return c.substring(name.length,c.length);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
// main search functionality
|
||||
var last_filter = "";
|
||||
function updateSearch() {
|
||||
var filter = document.getElementById('filter').value.toLowerCase();
|
||||
var vars_ol = document.getElementById("vars");
|
||||
|
||||
if (filter === last_filter) {
|
||||
// An event triggered an update but nothing has changed.
|
||||
return;
|
||||
} else if (filter.indexOf(last_filter) === 0) {
|
||||
// The new filter starts with the old filter, fast path by removing only.
|
||||
var children = vars_ol.childNodes;
|
||||
for (var i = children.length - 1; i >= 0; --i) {
|
||||
try {
|
||||
var li = children\[i];
|
||||
if (li.innerText.toLowerCase().indexOf(filter) == -1) {
|
||||
vars_ol.removeChild(li);
|
||||
}
|
||||
} catch(err) {}
|
||||
}
|
||||
} else {
|
||||
// Remove everything and put back what matches.
|
||||
while (vars_ol.hasChildNodes()) {
|
||||
vars_ol.removeChild(vars_ol.lastChild);
|
||||
}
|
||||
|
||||
for (var i = 0; i < complete_list.length; ++i) {
|
||||
try {
|
||||
var li = complete_list\[i];
|
||||
if (!filter || li.innerText.toLowerCase().indexOf(filter) != -1) {
|
||||
vars_ol.appendChild(li);
|
||||
}
|
||||
} catch(err) {}
|
||||
}
|
||||
}
|
||||
|
||||
last_filter = filter;
|
||||
document.cookie="[refid][cookieoffset]search="+encodeURIComponent(filter);
|
||||
|
||||
}
|
||||
|
||||
// onkeydown
|
||||
function handle_keydown() {
|
||||
if(event.keyCode == 116) { //F5 (to refresh properly)
|
||||
document.getElementById("refresh_link").click();
|
||||
event.preventDefault ? event.preventDefault() : (event.returnValue = false);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
// onkeyup
|
||||
function handle_keyup() {
|
||||
updateSearch();
|
||||
}
|
||||
|
||||
// onchange
|
||||
function handle_dropdown(list) {
|
||||
var value = list.options\[list.selectedIndex].value;
|
||||
if (value !== "") {
|
||||
location.href = value;
|
||||
}
|
||||
list.selectedIndex = 0;
|
||||
document.getElementById('filter').focus();
|
||||
}
|
||||
|
||||
// byjax
|
||||
function replace_span(what) {
|
||||
var idx = what.indexOf(':');
|
||||
document.getElementById(what.substr(0, idx)).innerHTML = what.substr(idx + 1);
|
||||
}
|
||||
</script>
|
||||
<div align='center'>
|
||||
<table width='100%'>
|
||||
<tr>
|
||||
<td width='50%'>
|
||||
<table align='center' width='100%'>
|
||||
<tr>
|
||||
<td>
|
||||
[sprite_text]
|
||||
<div align='center'>
|
||||
[header.Join()]
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
<div align='center'>
|
||||
<b><font size='1'>[formatted_type]</font></b>
|
||||
<span id='marked'>[marked]</span>
|
||||
<span id='varedited'>[varedited_line]</span>
|
||||
<span id='deleted'>[deleted_line]</span>
|
||||
</div>
|
||||
</td>
|
||||
<td width='50%'>
|
||||
<div align='center'>
|
||||
<a id='refresh_link' href='?_src_=vars;
|
||||
datumrefresh=[refid]'>Refresh</a>
|
||||
<form>
|
||||
<select name="file" size="1"
|
||||
onchange="handle_dropdown(this)"
|
||||
onmouseclick="this.focus()">
|
||||
<option value selected>Select option</option>
|
||||
[dropdownoptions_html.Join()]
|
||||
</select>
|
||||
</form>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
<hr>
|
||||
<font size='1'>
|
||||
<b>E</b> - Edit, tries to determine the variable type by itself.<br>
|
||||
<b>C</b> - Change, asks you for the var type first.<br>
|
||||
<b>M</b> - Mass modify: changes this variable for all objects of this type.<br>
|
||||
</font>
|
||||
<hr>
|
||||
<table width='100%'>
|
||||
<tr>
|
||||
<td width='20%'>
|
||||
<div align='center'>
|
||||
<b>Search:</b>
|
||||
</div>
|
||||
</td>
|
||||
<td width='80%'>
|
||||
<input type='text' id='filter' name='filter_text' value='' style='width:100%;'>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
<hr>
|
||||
<ol id='vars'>
|
||||
[variable_html.Join()]
|
||||
</ol>
|
||||
<script type='text/javascript'>
|
||||
var complete_list = \[\];
|
||||
var lis = document.getElementById("vars").children;
|
||||
for(var i = lis.length; i--;) complete_list\[i\] = lis\[i\];
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
"}
|
||||
src << browse(html, "window=variables[refid];size=475x650") //VOREStation edit end
|
||||
|
||||
/client/proc/vv_update_display(datum/D, span, content)
|
||||
src << output("[span]:[content]", "variables\ref[D].browser:replace_span")
|
||||
/client/proc/debug_variables(datum/D in world)
|
||||
set category = "Debug"
|
||||
set name = "View Variables"
|
||||
//set src in world
|
||||
var/static/cookieoffset = rand(1, 9999) //to force cookies to reset after the round.
|
||||
|
||||
if(!usr.client || !usr.client.holder) //The usr vs src abuse in this proc is intentional and must not be changed
|
||||
to_chat(usr, "<span class='danger'>You need to be an administrator to access this.</span>")
|
||||
return
|
||||
|
||||
if(!D)
|
||||
return
|
||||
|
||||
var/islist = islist(D)
|
||||
if (!islist && !istype(D))
|
||||
return
|
||||
|
||||
//VOREStation Edit Start - the rest of this proc in a spawn
|
||||
spawn(0)
|
||||
var/title = ""
|
||||
var/refid = "\ref[D]"
|
||||
var/icon/sprite
|
||||
var/hash
|
||||
|
||||
var/type = /list
|
||||
if (!islist)
|
||||
type = D.type
|
||||
|
||||
if(istype(D, /atom))
|
||||
var/atom/AT = D
|
||||
if(AT.icon && AT.icon_state)
|
||||
sprite = new /icon(AT.icon, AT.icon_state)
|
||||
hash = md5(AT.icon)
|
||||
hash = md5(hash + AT.icon_state)
|
||||
src << browse_rsc(sprite, "vv[hash].png")
|
||||
|
||||
title = "[D] (\ref[D]) = [type]"
|
||||
var/formatted_type = replacetext("[type]", "/", "<wbr>/")
|
||||
|
||||
var/sprite_text
|
||||
if(sprite)
|
||||
sprite_text = "<img src='vv[hash].png'></td><td>"
|
||||
var/list/header = islist(D)? list("<b>/list</b>") : D.vv_get_header()
|
||||
|
||||
var/marked
|
||||
if(holder && holder.marked_datum && holder.marked_datum == D)
|
||||
marked = VV_MSG_MARKED
|
||||
var/varedited_line = ""
|
||||
if(!islist && (D.datum_flags & DF_VAR_EDITED))
|
||||
varedited_line = VV_MSG_EDITED
|
||||
var/deleted_line
|
||||
if(!islist && D.gc_destroyed)
|
||||
deleted_line = VV_MSG_DELETED
|
||||
|
||||
var/list/dropdownoptions = list()
|
||||
var/autoconvert_dropdown = FALSE
|
||||
if (islist)
|
||||
dropdownoptions = list(
|
||||
"---",
|
||||
"Add Item" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_ADD]=TRUE;target=[refid]",
|
||||
"Remove Nulls" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_ERASE_NULLS]=TRUE;target=[refid]",
|
||||
"Remove Dupes" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_ERASE_DUPES]=TRUE;target=[refid]",
|
||||
"Set len" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_SET_LENGTH]=TRUE;target=[refid]",
|
||||
"Shuffle" = "?_src_=vars;[HrefToken()];[VV_HK_LIST_SHUFFLE]=TRUE;target=[refid]",
|
||||
// "Show VV To Player" = "?_src_=vars;[HrefToken()];[VV_HK_EXPOSE]=TRUE;target=[refid]" // TODO - Not yet implemented for lists
|
||||
)
|
||||
autoconvert_dropdown = TRUE
|
||||
else
|
||||
dropdownoptions = D.vv_get_dropdown()
|
||||
var/list/dropdownoptions_html = list()
|
||||
if(autoconvert_dropdown)
|
||||
for (var/name in dropdownoptions)
|
||||
var/link = dropdownoptions[name]
|
||||
if (link)
|
||||
dropdownoptions_html += "<option value='[link]'>[name]</option>"
|
||||
else
|
||||
dropdownoptions_html += "<option value>[name]</option>"
|
||||
else
|
||||
dropdownoptions_html = dropdownoptions + D.get_view_variables_options()
|
||||
|
||||
var/list/names = list()
|
||||
if (!islist)
|
||||
names = D.get_variables()
|
||||
//sleep(1)//For some reason, without this sleep, VVing will cause client to disconnect on certain objects. //VOREStation edit - commented out, replaced with spawn(0) above
|
||||
|
||||
var/list/variable_html = list()
|
||||
if (islist)
|
||||
var/list/L = D
|
||||
for (var/i in 1 to L.len)
|
||||
var/key = L[i]
|
||||
var/value
|
||||
if (IS_NORMAL_LIST(L) && IS_VALID_ASSOC_KEY(key))
|
||||
value = L[key]
|
||||
variable_html += debug_variable(i, value, 0, D)
|
||||
else
|
||||
|
||||
names = sortList(names)
|
||||
for (var/V in names)
|
||||
if(D.can_vv_get(V))
|
||||
variable_html += D.vv_get_var(V)
|
||||
|
||||
var/html = {"
|
||||
<html>
|
||||
<head>
|
||||
<title>[title]</title>
|
||||
<style>
|
||||
body {
|
||||
font-family: Verdana, sans-serif;
|
||||
font-size: 9pt;
|
||||
}
|
||||
.value {
|
||||
font-family: "Courier New", monospace;
|
||||
font-size: 8pt;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body onload='selectTextField()' onkeydown='return handle_keydown()' onkeyup='handle_keyup()'>
|
||||
<script type="text/javascript">
|
||||
// onload
|
||||
function selectTextField() {
|
||||
var filter_text = document.getElementById('filter');
|
||||
filter_text.focus();
|
||||
filter_text.select();
|
||||
var lastsearch = getCookie("[refid][cookieoffset]search");
|
||||
if (lastsearch) {
|
||||
filter_text.value = lastsearch;
|
||||
updateSearch();
|
||||
}
|
||||
}
|
||||
function getCookie(cname) {
|
||||
var name = cname + "=";
|
||||
var ca = document.cookie.split(';');
|
||||
for(var i=0; i<ca.length; i++) {
|
||||
var c = ca\[i];
|
||||
while (c.charAt(0)==' ') c = c.substring(1,c.length);
|
||||
if (c.indexOf(name)==0) return c.substring(name.length,c.length);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
// main search functionality
|
||||
var last_filter = "";
|
||||
function updateSearch() {
|
||||
var filter = document.getElementById('filter').value.toLowerCase();
|
||||
var vars_ol = document.getElementById("vars");
|
||||
|
||||
if (filter === last_filter) {
|
||||
// An event triggered an update but nothing has changed.
|
||||
return;
|
||||
} else if (filter.indexOf(last_filter) === 0) {
|
||||
// The new filter starts with the old filter, fast path by removing only.
|
||||
var children = vars_ol.childNodes;
|
||||
for (var i = children.length - 1; i >= 0; --i) {
|
||||
try {
|
||||
var li = children\[i];
|
||||
if (li.innerText.toLowerCase().indexOf(filter) == -1) {
|
||||
vars_ol.removeChild(li);
|
||||
}
|
||||
} catch(err) {}
|
||||
}
|
||||
} else {
|
||||
// Remove everything and put back what matches.
|
||||
while (vars_ol.hasChildNodes()) {
|
||||
vars_ol.removeChild(vars_ol.lastChild);
|
||||
}
|
||||
|
||||
for (var i = 0; i < complete_list.length; ++i) {
|
||||
try {
|
||||
var li = complete_list\[i];
|
||||
if (!filter || li.innerText.toLowerCase().indexOf(filter) != -1) {
|
||||
vars_ol.appendChild(li);
|
||||
}
|
||||
} catch(err) {}
|
||||
}
|
||||
}
|
||||
|
||||
last_filter = filter;
|
||||
document.cookie="[refid][cookieoffset]search="+encodeURIComponent(filter);
|
||||
|
||||
}
|
||||
|
||||
// onkeydown
|
||||
function handle_keydown() {
|
||||
if(event.keyCode == 116) { //F5 (to refresh properly)
|
||||
document.getElementById("refresh_link").click();
|
||||
event.preventDefault ? event.preventDefault() : (event.returnValue = false);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
// onkeyup
|
||||
function handle_keyup() {
|
||||
updateSearch();
|
||||
}
|
||||
|
||||
// onchange
|
||||
function handle_dropdown(list) {
|
||||
var value = list.options\[list.selectedIndex].value;
|
||||
if (value !== "") {
|
||||
location.href = value;
|
||||
}
|
||||
list.selectedIndex = 0;
|
||||
document.getElementById('filter').focus();
|
||||
}
|
||||
|
||||
// byjax
|
||||
function replace_span(what) {
|
||||
var idx = what.indexOf(':');
|
||||
document.getElementById(what.substr(0, idx)).innerHTML = what.substr(idx + 1);
|
||||
}
|
||||
</script>
|
||||
<div align='center'>
|
||||
<table width='100%'>
|
||||
<tr>
|
||||
<td width='50%'>
|
||||
<table align='center' width='100%'>
|
||||
<tr>
|
||||
<td>
|
||||
[sprite_text]
|
||||
<div align='center'>
|
||||
[header.Join()]
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
<div align='center'>
|
||||
<b><font size='1'>[formatted_type]</font></b>
|
||||
<span id='marked'>[marked]</span>
|
||||
<span id='varedited'>[varedited_line]</span>
|
||||
<span id='deleted'>[deleted_line]</span>
|
||||
</div>
|
||||
</td>
|
||||
<td width='50%'>
|
||||
<div align='center'>
|
||||
<a id='refresh_link' href='?_src_=vars;
|
||||
datumrefresh=[refid]'>Refresh</a>
|
||||
<form>
|
||||
<select name="file" size="1"
|
||||
onchange="handle_dropdown(this)"
|
||||
onmouseclick="this.focus()">
|
||||
<option value selected>Select option</option>
|
||||
[dropdownoptions_html.Join()]
|
||||
</select>
|
||||
</form>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
<hr>
|
||||
<font size='1'>
|
||||
<b>E</b> - Edit, tries to determine the variable type by itself.<br>
|
||||
<b>C</b> - Change, asks you for the var type first.<br>
|
||||
<b>M</b> - Mass modify: changes this variable for all objects of this type.<br>
|
||||
</font>
|
||||
<hr>
|
||||
<table width='100%'>
|
||||
<tr>
|
||||
<td width='20%'>
|
||||
<div align='center'>
|
||||
<b>Search:</b>
|
||||
</div>
|
||||
</td>
|
||||
<td width='80%'>
|
||||
<input type='text' id='filter' name='filter_text' value='' style='width:100%;'>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
<hr>
|
||||
<ol id='vars'>
|
||||
[variable_html.Join()]
|
||||
</ol>
|
||||
<script type='text/javascript'>
|
||||
var complete_list = \[\];
|
||||
var lis = document.getElementById("vars").children;
|
||||
for(var i = lis.length; i--;) complete_list\[i\] = lis\[i\];
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
"}
|
||||
src << browse(html, "window=variables[refid];size=475x650") //VOREStation edit end
|
||||
|
||||
/client/proc/vv_update_display(datum/D, span, content)
|
||||
src << output("[span]:[content]", "variables\ref[D].browser:replace_span")
|
||||
|
||||
Reference in New Issue
Block a user