mirror of
https://github.com/CHOMPStation2/CHOMPStation2.git
synced 2025-12-11 10:43:20 +00:00
[MIRROR] some fixes (#10581)
Co-authored-by: Kashargul <144968721+Kashargul@users.noreply.github.com>
This commit is contained in:
committed by
GitHub
parent
18825ed294
commit
99dfe34765
@@ -4,19 +4,18 @@
|
||||
var/window_id // window_id is used as the window name for browse and onclose
|
||||
var/width = 0
|
||||
var/height = 0
|
||||
var/atom/ref = null
|
||||
var/window_options = "focus=0;can_close=1;can_minimize=1;can_maximize=0;can_resize=1;titlebar=1;" // window option is set using window_id
|
||||
var/datum/weakref/ref = null
|
||||
var/window_options = "can_close=1;can_minimize=1;can_maximize=0;can_resize=1;titlebar=1;" // window option is set using window_id
|
||||
var/stylesheets[0]
|
||||
var/scripts[0]
|
||||
var/title_image
|
||||
var/head_elements
|
||||
var/body_elements
|
||||
var/head_content = ""
|
||||
var/content = ""
|
||||
var/title_buttons = ""
|
||||
|
||||
/datum/browser/New(nuser, nwindow_id, ntitle = 0, nwidth = 0, nheight = 0, var/atom/nref = null)
|
||||
/datum/browser/New(nuser, nwindow_id, ntitle = 0, nwidth = 0, nheight = 0, atom/nref = null)
|
||||
user = nuser
|
||||
RegisterSignal(user, COMSIG_PARENT_QDELETING, PROC_REF(user_deleted))
|
||||
window_id = nwindow_id
|
||||
if (ntitle)
|
||||
title = format_text(ntitle)
|
||||
@@ -25,40 +24,36 @@
|
||||
if (nheight)
|
||||
height = nheight
|
||||
if (nref)
|
||||
ref = nref
|
||||
// If a client exists, but they have disabled fancy windowing, disable it!
|
||||
if(!user?.client?.prefs?.read_preference(/datum/preference/toggle/browser_style))
|
||||
return
|
||||
add_stylesheet("common", 'html/browser/common.css') // this CSS sheet is common to all UIs
|
||||
ref = WEAKREF(nref)
|
||||
|
||||
//VOREStation Edit - Allow browser datums to be garbage collected
|
||||
/datum/browser/Destroy()
|
||||
close()
|
||||
ref = null
|
||||
/datum/browser/proc/user_deleted(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
user = null
|
||||
. = ..()
|
||||
//VOREStation Edit End - Allow browser datums to be garbage collected
|
||||
|
||||
/datum/browser/proc/set_title(ntitle)
|
||||
title = format_text(ntitle)
|
||||
|
||||
/datum/browser/proc/add_head_content(nhead_content)
|
||||
head_content = nhead_content
|
||||
|
||||
/datum/browser/proc/set_title_buttons(ntitle_buttons)
|
||||
title_buttons = ntitle_buttons
|
||||
|
||||
/datum/browser/proc/set_window_options(nwindow_options)
|
||||
window_options = nwindow_options
|
||||
|
||||
/datum/browser/proc/set_title_image(ntitle_image)
|
||||
//title_image = ntitle_image
|
||||
|
||||
/datum/browser/proc/add_stylesheet(name, file)
|
||||
stylesheets[name] = file
|
||||
if (istype(name, /datum/asset/spritesheet))
|
||||
var/datum/asset/spritesheet/sheet = name
|
||||
stylesheets["spritesheet_[sheet.name].css"] = "data/spritesheets/[sheet.name]"
|
||||
else if (istype(name, /datum/asset/spritesheet_batched))
|
||||
var/datum/asset/spritesheet_batched/sheet = name
|
||||
stylesheets["spritesheet_[sheet.name].css"] = "data/spritesheets/[sheet.name]"
|
||||
else
|
||||
var/asset_name = "[name].css"
|
||||
|
||||
stylesheets[asset_name] = file
|
||||
|
||||
if (!SSassets.cache[asset_name])
|
||||
SSassets.transport.register_asset(asset_name, file)
|
||||
|
||||
/datum/browser/proc/add_script(name, file)
|
||||
scripts[name] = file
|
||||
scripts["[ckey(name)].js"] = file
|
||||
SSassets.transport.register_asset("[ckey(name)].js", file)
|
||||
|
||||
/datum/browser/proc/set_content(ncontent)
|
||||
content = ncontent
|
||||
@@ -67,25 +62,21 @@
|
||||
content += ncontent
|
||||
|
||||
/datum/browser/proc/get_header()
|
||||
var/key
|
||||
var/filename
|
||||
for (key in stylesheets)
|
||||
filename = "[ckey(key)].css"
|
||||
user << browse_rsc(stylesheets[key], filename)
|
||||
head_content += "<link rel='stylesheet' type='text/css' href='[filename]'>"
|
||||
var/datum/asset/simple/namespaced/common/common_asset = get_asset_datum(/datum/asset/simple/namespaced/common)
|
||||
var/file
|
||||
|
||||
for (key in scripts)
|
||||
filename = "[ckey(key)].js"
|
||||
user << browse_rsc(scripts[key], filename)
|
||||
head_content += "<script type='text/javascript' src='[filename]'></script>"
|
||||
// If a client exists, but they have disabled fancy windowing, disable it!
|
||||
if(user?.client?.prefs?.read_preference(/datum/preference/toggle/browser_style))
|
||||
head_content += "<link rel='stylesheet' type='text/css' href='[common_asset.get_url_mappings()["common.css"]]'>"
|
||||
for (file in stylesheets)
|
||||
head_content += "<link rel='stylesheet' type='text/css' href='[SSassets.transport.get_asset_url(file)]'>"
|
||||
|
||||
var/title_attributes = "class='uiTitle'"
|
||||
if (title_image)
|
||||
title_attributes = "class='uiTitle icon' style='background-image: url([title_image]);'"
|
||||
|
||||
return {"<!DOCTYPE html>
|
||||
for (file in scripts)
|
||||
head_content += "<script type='text/javascript' src='[SSassets.transport.get_asset_url(file)]'></script>"
|
||||
|
||||
return {"<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
|
||||
<html>
|
||||
<meta charset=ISO-8859-1">
|
||||
<head>
|
||||
<meta http-equiv='Content-Type' content='text/html; charset=UTF-8'>
|
||||
<meta http-equiv='X-UA-Compatible' content='IE=edge'>
|
||||
@@ -93,10 +84,10 @@
|
||||
</head>
|
||||
<body scroll=auto>
|
||||
<div class='uiWrapper'>
|
||||
[title ? "<div class='uiTitleWrapper'><div [title_attributes]><tt>[title]</tt></div><div class='uiTitleButtons'>[title_buttons]</div></div>" : ""]
|
||||
[title ? "<div class='uiTitleWrapper'><div class='uiTitle'><tt>[title]</tt></div></div>" : ""]
|
||||
<div class='uiContent'>
|
||||
"}
|
||||
|
||||
//" This is here because else the rest of the file looks like a string in notepad++.
|
||||
/datum/browser/proc/get_footer()
|
||||
return {"
|
||||
</div>
|
||||
@@ -111,85 +102,35 @@
|
||||
[get_footer()]
|
||||
"}
|
||||
|
||||
/datum/browser/proc/open(var/use_onclose = 1)
|
||||
if(isnull(window_id)) //null check because this can potentially nuke goonchat
|
||||
/datum/browser/proc/open(use_onclose = TRUE)
|
||||
if(isnull(window_id)) //null check because this can potentially nuke goonchat
|
||||
WARNING("Browser [title] tried to open with a null ID")
|
||||
to_chat(user, span_userdanger("The [title] browser you tried to open failed a sanity check! Please report this on github!"))
|
||||
to_chat(user, span_userdanger("The [title] browser you tried to open failed a sanity check! Please report this on GitHub!"))
|
||||
return
|
||||
var/window_size = ""
|
||||
if (width && height)
|
||||
window_size = "size=[width]x[height];"
|
||||
var/datum/asset/simple/namespaced/common/common_asset = get_asset_datum(/datum/asset/simple/namespaced/common)
|
||||
common_asset.send(user)
|
||||
if (stylesheets.len)
|
||||
SSassets.transport.send_assets(user, stylesheets)
|
||||
if (scripts.len)
|
||||
SSassets.transport.send_assets(user, scripts)
|
||||
user << browse(get_content(), "window=[window_id];[window_size][window_options]")
|
||||
if (use_onclose)
|
||||
onclose(user, window_id, ref)
|
||||
setup_onclose()
|
||||
|
||||
// This will allow you to show an icon in the browse window
|
||||
// This is added to mob so that it can be used without a reference to the browser object
|
||||
// There is probably a better place for this...
|
||||
/mob/proc/browse_rsc_icon(icon, icon_state, dir = -1)
|
||||
/*
|
||||
var/icon/I
|
||||
if (dir >= 0)
|
||||
I = new /icon(icon, icon_state, dir)
|
||||
else
|
||||
I = new /icon(icon, icon_state)
|
||||
dir = "default"
|
||||
|
||||
var/filename = "[ckey("[icon]_[icon_state]_[dir]")].png"
|
||||
src << browse_rsc(I, filename)
|
||||
return filename
|
||||
*/
|
||||
|
||||
|
||||
// Registers the on-close verb for a browse window (client/verb/.windowclose)
|
||||
// this will be called when the close-button of a window is pressed.
|
||||
//
|
||||
// This is usually only needed for devices that regularly update the browse window,
|
||||
// e.g. canisters, timers, etc.
|
||||
//
|
||||
// windowid should be the specified window name
|
||||
// e.g. code is : user << browse(text, "window=fred")
|
||||
// then use : onclose(user, "fred")
|
||||
//
|
||||
// Optionally, specify the "ref" parameter as the controlled atom (usually src)
|
||||
// to pass a "close=1" parameter to the atom's Topic() proc for special handling.
|
||||
// Otherwise, the user mob's machine var will be reset directly.
|
||||
//
|
||||
/proc/onclose(mob/user, windowid, var/atom/ref=null)
|
||||
if(!user || !user.client) return
|
||||
var/param = "null"
|
||||
if(ref)
|
||||
param = "\ref[ref]"
|
||||
|
||||
winset(user, windowid, "on-close=\".windowclose [param]\"")
|
||||
|
||||
//to_world("OnClose [user]: [windowid] : ["on-close=\".windowclose [param]\""]")
|
||||
|
||||
// the on-close client verb
|
||||
// called when a browser popup window is closed after registering with proc/onclose()
|
||||
// if a valid atom reference is supplied, call the atom's Topic() with "close=1"
|
||||
// otherwise, just reset the client mob's machine var.
|
||||
//
|
||||
|
||||
/client/verb/windowclose(var/atomref as text)
|
||||
set hidden = 1 // hide this verb from the user's panel
|
||||
set name = ".windowclose" // no autocomplete on cmd line
|
||||
|
||||
//to_world("windowclose: [atomref]")
|
||||
if(atomref!="null") // if passed a real atomref
|
||||
var/hsrc = locate(atomref) // find the reffed atom
|
||||
if(hsrc)
|
||||
//to_world("[src] Topic [href] [hsrc]")
|
||||
usr = src.mob
|
||||
src.Topic("close=1", list("close"="1"), hsrc) // this will direct to the atom's
|
||||
return // Topic() proc via client.Topic()
|
||||
|
||||
// no atomref specified (or not found)
|
||||
// so just reset the user mob's machine var
|
||||
if(src && src.mob)
|
||||
//to_world("[src] was [src.mob.machine], setting to null")
|
||||
src.mob.unset_machine()
|
||||
return
|
||||
/datum/browser/proc/setup_onclose()
|
||||
set waitfor = 0 //winexists sleeps, so we don't need to.
|
||||
for (var/i in 1 to 10)
|
||||
if (user?.client && winexists(user, window_id))
|
||||
var/atom/send_ref
|
||||
if(ref)
|
||||
send_ref = ref.resolve()
|
||||
if(!send_ref)
|
||||
ref = null
|
||||
onclose(user, window_id, send_ref)
|
||||
break
|
||||
|
||||
/datum/browser/proc/close()
|
||||
if(!isnull(window_id))//null check because this can potentially nuke goonchat
|
||||
@@ -201,15 +142,15 @@
|
||||
if (!User)
|
||||
return
|
||||
|
||||
var/output = {"<center><b>[Message]</b></center><br />
|
||||
var/output = {"<center><b>[Message]</b></center><br />
|
||||
<div style="text-align:center">
|
||||
<a style="font-size:large;float:[( Button2 ? "left" : "right" )]" href="byond://?src=\ref[src];button=1">[Button1]</a>"}
|
||||
<a style="font-size:large;float:[( Button2 ? "left" : "right" )]" href='byond://?src=[REF(src)];button=1'>[Button1]</a>"}
|
||||
|
||||
if (Button2)
|
||||
output += {"<a style="font-size:large;[( Button3 ? "" : "float:right" )]" href="byond://?src=\ref[src];button=2">[Button2]</a>"}
|
||||
output += {"<a style="font-size:large;[( Button3 ? "" : "float:right" )]" href='byond://?src=[REF(src)];button=2'>[Button2]</a>"}
|
||||
|
||||
if (Button3)
|
||||
output += {"<a style="font-size:large;float:right" href="byond://?src=\ref[src];button=3">[Button3]</a>"}
|
||||
output += {"<a style="font-size:large;float:right" href='byond://?src=[REF(src)];button=3'>[Button3]</a>"}
|
||||
|
||||
output += {"</div>"}
|
||||
|
||||
@@ -227,11 +168,35 @@
|
||||
opentime = 0
|
||||
close()
|
||||
|
||||
//designed as a drop in replacement for alert(); functions the same. (outside of needing User specified)
|
||||
/proc/tgalert(var/mob/User, Message, Title, Button1="Ok", Button2, Button3, StealFocus = 1, Timeout = 6000)
|
||||
/**
|
||||
* **DEPRECATED: USE tgui_alert(...) INSTEAD**
|
||||
*
|
||||
* Designed as a drop in replacement for alert(); functions the same. (outside of needing User specified)
|
||||
* Arguments:
|
||||
* * User - The user to show the alert to.
|
||||
* * Message - The textual body of the alert.
|
||||
* * Title - The title of the alert's window.
|
||||
* * Button1 - The first button option.
|
||||
* * Button2 - The second button option.
|
||||
* * Button3 - The third button option.
|
||||
* * StealFocus - Boolean operator controlling if the alert will steal the user's window focus.
|
||||
* * Timeout - The timeout of the window, after which no responses will be valid.
|
||||
*/
|
||||
/proc/tgalert(mob/User, Message, Title, Button1="Ok", Button2, Button3, StealFocus = TRUE, Timeout = 6000)
|
||||
if (!User)
|
||||
User = usr
|
||||
switch(askuser(User, Message, Title, Button1, Button2, Button3, StealFocus, Timeout))
|
||||
if (!istype(User))
|
||||
if (istype(User, /client))
|
||||
var/client/client = User
|
||||
User = client.mob
|
||||
else
|
||||
return
|
||||
|
||||
// Get user's response using a modal
|
||||
var/datum/browser/modal/alert/A = new(User, Message, Title, Button1, Button2, Button3, StealFocus, Timeout)
|
||||
A.open()
|
||||
A.wait()
|
||||
switch(A.selectedbutton)
|
||||
if (1)
|
||||
return Button1
|
||||
if (2)
|
||||
@@ -239,27 +204,13 @@
|
||||
if (3)
|
||||
return Button3
|
||||
|
||||
//Same shit, but it returns the button number, could at some point support unlimited button amounts.
|
||||
/proc/askuser(var/mob/User,Message, Title, Button1="Ok", Button2, Button3, StealFocus = 1, Timeout = 6000)
|
||||
if (!istype(User))
|
||||
if (istype(User, /client/))
|
||||
var/client/C = User
|
||||
User = C.mob
|
||||
else
|
||||
return
|
||||
var/datum/browser/modal/alert/A = new(User, Message, Title, Button1, Button2, Button3, StealFocus, Timeout)
|
||||
A.open()
|
||||
A.wait()
|
||||
if (A.selectedbutton)
|
||||
return A.selectedbutton
|
||||
|
||||
/datum/browser/modal
|
||||
var/opentime = 0
|
||||
var/timeout
|
||||
var/selectedbutton = 0
|
||||
var/stealfocus
|
||||
|
||||
/datum/browser/modal/New(nuser, nwindow_id, ntitle = 0, nwidth = 0, nheight = 0, var/atom/nref = null, StealFocus = 1, Timeout = 6000)
|
||||
/datum/browser/modal/New(nuser, nwindow_id, ntitle = 0, nwidth = 0, nheight = 0, atom/nref = null, StealFocus = 1, Timeout = 6000)
|
||||
..()
|
||||
stealfocus = StealFocus
|
||||
if (!StealFocus)
|
||||
@@ -271,8 +222,8 @@
|
||||
.=..()
|
||||
opentime = 0
|
||||
|
||||
/datum/browser/modal/open()
|
||||
set waitfor = 0
|
||||
/datum/browser/modal/open(use_onclose)
|
||||
set waitfor = FALSE
|
||||
opentime = world.time
|
||||
|
||||
if (stealfocus)
|
||||
@@ -304,12 +255,16 @@
|
||||
if (!User)
|
||||
return
|
||||
|
||||
var/output = {"<form><input type="hidden" name="src" value="\ref[src]"><ul class="sparse">"}
|
||||
var/output = {"<form><input type="hidden" name="src" value="[REF(src)]"><ul class="sparse">"}
|
||||
if (inputtype == "checkbox" || inputtype == "radio")
|
||||
for (var/i in values)
|
||||
var/div_slider = slidecolor
|
||||
if(!i["allowed_edit"])
|
||||
div_slider = "locked"
|
||||
output += {"<li>
|
||||
<label class="switch">
|
||||
<input type="[inputtype]" value="1" name="[i["name"]]"[i["checked"] ? " checked" : ""][i["allowed_edit"] ? "" : " disabled onclick='return false' onkeydown='return false'"]>
|
||||
<input type="[inputtype]" value="1" name="[i["name"]]"[i["checked"] ? " checked" : ""][i["allowed_edit"] ? "" : " onclick='return false' onkeydown='return false'"]>
|
||||
<div class="slider [div_slider ? "[div_slider]" : ""]"></div>
|
||||
<span>[i["name"]]</span>
|
||||
</label>
|
||||
</li>"}
|
||||
@@ -347,7 +302,7 @@
|
||||
opentime = 0
|
||||
close()
|
||||
|
||||
/proc/presentpicker(var/mob/User,Message, Title, Button1="Ok", Button2, Button3, StealFocus = 1,Timeout = 6000,list/values, inputtype = "checkbox", width, height, slidecolor)
|
||||
/proc/presentpicker(mob/User,Message, Title, Button1="Ok", Button2, Button3, StealFocus = 1,Timeout = 6000,list/values, inputtype = "checkbox", width, height, slidecolor)
|
||||
if (!istype(User))
|
||||
if (istype(User, /client/))
|
||||
var/client/C = User
|
||||
@@ -381,6 +336,35 @@
|
||||
. |= GLOB.bitfields[bitfield][flag]
|
||||
else
|
||||
return
|
||||
//
|
||||
/proc/onclose(mob/user, windowid, atom/ref=null)
|
||||
if(!user.client)
|
||||
return
|
||||
var/param = "null"
|
||||
if(ref)
|
||||
param = "[REF(ref)]"
|
||||
|
||||
winset(user, windowid, "on-close=\".windowclose [param]\"")
|
||||
|
||||
|
||||
|
||||
// the on-close client verb
|
||||
// called when a browser popup window is closed after registering with proc/onclose()
|
||||
// if a valid atom reference is supplied, call the atom's Topic() with "close=1"
|
||||
// otherwise, just reset the client mob's machine var.
|
||||
//
|
||||
/client/verb/windowclose(atomref as text)
|
||||
set hidden = TRUE // hide this verb from the user's panel
|
||||
set name = ".windowclose" // no autocomplete on cmd line
|
||||
|
||||
if(atomref != "null") // if passed a real atomref
|
||||
var/hsrc = locate(atomref) // find the reffed atom
|
||||
var/href = "close=1"
|
||||
if(hsrc)
|
||||
usr = src.mob
|
||||
src.Topic(href, params2list(href), hsrc) // this will direct to the atom's
|
||||
return // Topic() proc via client.Topic()
|
||||
|
||||
|
||||
/datum/browser/modal/color_matrix_picker
|
||||
var/color_matrix
|
||||
|
||||
Reference in New Issue
Block a user