mirror of
https://github.com/Aurorastation/Aurora-Old.git
synced 2026-08-28 15:16:21 +01:00
Initial Commit
This commit is contained in:
@@ -0,0 +1,105 @@
|
||||
#define FORWARD -1
|
||||
#define BACKWARD 1
|
||||
|
||||
/datum/construction
|
||||
var/list/steps
|
||||
var/atom/holder
|
||||
var/result
|
||||
var/list/steps_desc
|
||||
|
||||
New(atom)
|
||||
..()
|
||||
holder = atom
|
||||
if(!holder) //don't want this without a holder
|
||||
spawn
|
||||
del src
|
||||
set_desc(steps.len)
|
||||
return
|
||||
|
||||
proc/next_step()
|
||||
steps.len--
|
||||
if(!steps.len)
|
||||
spawn_result()
|
||||
else
|
||||
set_desc(steps.len)
|
||||
return
|
||||
|
||||
proc/action(atom/used_atom,mob/user as mob)
|
||||
return
|
||||
|
||||
proc/check_step(atom/used_atom,mob/user as mob) //check last step only
|
||||
var/valid_step = is_right_key(used_atom)
|
||||
if(valid_step)
|
||||
if(custom_action(valid_step, used_atom, user))
|
||||
next_step()
|
||||
return 1
|
||||
return 0
|
||||
|
||||
proc/is_right_key(atom/used_atom) // returns current step num if used_atom is of the right type.
|
||||
var/list/L = steps[steps.len]
|
||||
if(istype(used_atom, L["key"]))
|
||||
return steps.len
|
||||
return 0
|
||||
|
||||
proc/custom_action(step, used_atom, user)
|
||||
return 1
|
||||
|
||||
proc/check_all_steps(atom/used_atom,mob/user as mob) //check all steps, remove matching one.
|
||||
for(var/i=1;i<=steps.len;i++)
|
||||
var/list/L = steps[i];
|
||||
if(istype(used_atom, L["key"]))
|
||||
if(custom_action(i, used_atom, user))
|
||||
steps[i]=null;//stupid byond list from list removal...
|
||||
listclearnulls(steps);
|
||||
if(!steps.len)
|
||||
spawn_result()
|
||||
return 1
|
||||
return 0
|
||||
|
||||
|
||||
proc/spawn_result()
|
||||
if(result)
|
||||
new result(get_turf(holder))
|
||||
spawn()
|
||||
del holder
|
||||
return
|
||||
|
||||
proc/set_desc(index as num)
|
||||
var/list/step = steps[index]
|
||||
holder.desc = step["desc"]
|
||||
return
|
||||
|
||||
/datum/construction/reversible
|
||||
var/index
|
||||
|
||||
New(atom)
|
||||
..()
|
||||
index = steps.len
|
||||
return
|
||||
|
||||
proc/update_index(diff as num)
|
||||
index+=diff
|
||||
if(index==0)
|
||||
spawn_result()
|
||||
else
|
||||
set_desc(index)
|
||||
return
|
||||
|
||||
is_right_key(atom/used_atom) // returns index step
|
||||
var/list/L = steps[index]
|
||||
if(istype(used_atom, L["key"]))
|
||||
return FORWARD //to the first step -> forward
|
||||
else if(L["backkey"] && istype(used_atom, L["backkey"]))
|
||||
return BACKWARD //to the last step -> backwards
|
||||
return 0
|
||||
|
||||
check_step(atom/used_atom,mob/user as mob)
|
||||
var/diff = is_right_key(used_atom)
|
||||
if(diff)
|
||||
if(custom_action(index, diff, used_atom, user))
|
||||
update_index(diff)
|
||||
return 1
|
||||
return 0
|
||||
|
||||
custom_action(index, diff, used_atom, user)
|
||||
return 1
|
||||
@@ -0,0 +1,67 @@
|
||||
/*
|
||||
* WARRANTY VOID IF CODE USED
|
||||
*/
|
||||
|
||||
|
||||
/datum/events
|
||||
var/list/events
|
||||
|
||||
New()
|
||||
..()
|
||||
events = new
|
||||
|
||||
proc/addEventType(event_type as text)
|
||||
if(!(event_type in events) || !islist(events[event_type]))
|
||||
events[event_type] = list()
|
||||
return 1
|
||||
return
|
||||
|
||||
|
||||
// Arguments: event_type as text, proc_holder as datum, proc_name as text
|
||||
// Returns: New event, null on error.
|
||||
proc/addEvent(event_type as text, proc_holder, proc_name as text)
|
||||
if(!event_type || !proc_holder || !proc_name)
|
||||
return
|
||||
addEventType(event_type)
|
||||
var/list/event = events[event_type]
|
||||
var/datum/event/E = new /datum/event(proc_holder,proc_name)
|
||||
event += E
|
||||
return E
|
||||
|
||||
// Arguments: event_type as text, any number of additional arguments to pass to event handler
|
||||
// Returns: null
|
||||
proc/fireEvent()
|
||||
//world << "Events in [args[1]] called"
|
||||
var/list/event = listgetindex(events,args[1])
|
||||
if(istype(event))
|
||||
spawn(-1)
|
||||
for(var/datum/event/E in event)
|
||||
if(!E.Fire(arglist(args.Copy(2))))
|
||||
clearEvent(args[1],E)
|
||||
return
|
||||
|
||||
// Arguments: event_type as text, E as /datum/event
|
||||
// Returns: 1 if event cleared, null on error
|
||||
proc/clearEvent(event_type as text, datum/event/E)
|
||||
if(!event_type || !E)
|
||||
return
|
||||
var/list/event = listgetindex(events,event_type)
|
||||
event -= E
|
||||
return 1
|
||||
|
||||
|
||||
/datum/event
|
||||
var/listener
|
||||
var/proc_name
|
||||
|
||||
New(tlistener,tprocname)
|
||||
listener = tlistener
|
||||
proc_name = tprocname
|
||||
return ..()
|
||||
|
||||
proc/Fire()
|
||||
//world << "Event fired"
|
||||
if(listener)
|
||||
call(listener,proc_name)(arglist(args))
|
||||
return 1
|
||||
return
|
||||
@@ -0,0 +1,96 @@
|
||||
/*
|
||||
* This datum gets revision info from local svn 'entries' file
|
||||
* Path to the directory containing it should be in 'config/svndir.txt' file
|
||||
*
|
||||
*/
|
||||
|
||||
var/global/datum/getrev/revdata = new("config/svndir.txt")
|
||||
|
||||
//Oh yeah, I'm an OOP fag, lalala
|
||||
/datum/getrev
|
||||
var/revision
|
||||
var/commiter
|
||||
var/svndirpath
|
||||
var/revhref
|
||||
|
||||
proc/abort()
|
||||
spawn()
|
||||
del src
|
||||
|
||||
New(filename)
|
||||
..()
|
||||
var/list/Lines = file2list(filename)
|
||||
if(!Lines.len) return abort()
|
||||
for(var/t in Lines)
|
||||
if(!t) continue
|
||||
t = trim(t)
|
||||
if (length(t) == 0)
|
||||
continue
|
||||
else if (copytext(t, 1, 2) == "#")
|
||||
continue
|
||||
var/pos = findtext(t, " ")
|
||||
var/name = null
|
||||
var/value = null
|
||||
if (pos)
|
||||
name = lowertext(copytext(t, 1, pos))
|
||||
value = copytext(t, pos + 1)
|
||||
else
|
||||
name = lowertext(t)
|
||||
if(!name)
|
||||
continue
|
||||
switch(name)
|
||||
if("svndir")
|
||||
svndirpath = value
|
||||
if("revhref")
|
||||
revhref = value
|
||||
|
||||
if(svndirpath && fexists(svndirpath) && fexists("[svndirpath]/entries") && isfile(file("[svndirpath]/entries")))
|
||||
var/list/filelist = file2list("[svndirpath]/entries")
|
||||
var/s_archive = "" //Stores the previous line so the revision owner can be assigned.
|
||||
|
||||
//This thing doesn't count blank lines, so doing filelist[4] isn't working.
|
||||
for(var/s in filelist)
|
||||
if(!commiter)
|
||||
if(s == "has-props")//The line before this is the committer.
|
||||
commiter = s_archive
|
||||
if(!revision)
|
||||
var/n = text2num(s)
|
||||
if(isnum(n))
|
||||
if(n > 5000 && n < 99999) //Do you think we'll still be up and running at r100000? :) ~Errorage
|
||||
revision = s
|
||||
if(revision && commiter)
|
||||
break
|
||||
s_archive = s
|
||||
if(!revision)
|
||||
abort()
|
||||
diary << "Revision info loaded succesfully"
|
||||
return
|
||||
return abort()
|
||||
|
||||
proc/getRevisionText()
|
||||
var/output
|
||||
if(revhref)
|
||||
output = {"<a href="[revhref][revision]">[revision]</a>"}
|
||||
else
|
||||
output = revision
|
||||
return output
|
||||
|
||||
proc/showInfo()
|
||||
return {"<html>
|
||||
<head>
|
||||
</head>
|
||||
<body>
|
||||
<p><b>Server Revision:</b> [getRevisionText()]<br/>
|
||||
<b>Author:</b> [commiter]</p>
|
||||
</body>
|
||||
<html>"}
|
||||
|
||||
client/verb/showrevinfo()
|
||||
set category = "OOC"
|
||||
set name = "Show Server Revision"
|
||||
var/output = "Sorry, the revision info is unavailable."
|
||||
output = file2text("/home/bay12/live/data/gitcommit")
|
||||
output += "Current Infomational Settings: <br>"
|
||||
output += "Protect Authority Roles From Tratior: [config.protect_roles_from_antagonist]<br>"
|
||||
usr << browse(output,"window=revdata");
|
||||
return
|
||||
@@ -0,0 +1,154 @@
|
||||
/*
|
||||
README:
|
||||
|
||||
The global_iterator datum is supposed to provide a simple and robust way to
|
||||
create some constantly "looping" processes with ability to stop and restart them at will.
|
||||
Generally, the only thing you want to play with (meaning, redefine) is the process() proc.
|
||||
It must contain all the things you want done.
|
||||
|
||||
Control functions:
|
||||
new - used to create datum. First argument (optional) - var list(to use in process() proc) as list,
|
||||
second (optional) - autostart control.
|
||||
If autostart == TRUE, the loop will be started immediately after datum creation.
|
||||
|
||||
start(list/arguments) - starts the loop. Takes arguments(optional) as a list, which is then used
|
||||
by process() proc. Returns null if datum already active, 1 if loop started succesfully and 0 if there's
|
||||
an error in supplied arguments (not list or empty list).
|
||||
|
||||
stop() - stops the loop. Returns null if datum is already inactive and 1 on success.
|
||||
|
||||
set_delay(new_delay) - sets the delay between iterations. Pretty selfexplanatory.
|
||||
Returns 0 on error(new_delay is not numerical), 1 otherwise.
|
||||
|
||||
set_process_args(list/arguments) - passes the supplied arguments to the process() proc.
|
||||
|
||||
active() - Returns 1 if datum is active, 0 otherwise.
|
||||
|
||||
toggle() - toggles datum state. Returns new datum state (see active()).
|
||||
|
||||
Misc functions:
|
||||
|
||||
get_last_exec_time() - Returns the time of last iteration.
|
||||
|
||||
get_last_exec_time_as_text() - Returns the time of last iteration as text
|
||||
|
||||
|
||||
Control vars:
|
||||
|
||||
delay - delay between iterations
|
||||
|
||||
check_for_null - if equals TRUE, on each iteration the supplied arguments will be checked for nulls.
|
||||
If some varible equals null (and null only), the loop is stopped.
|
||||
Usefull, if some var unexpectedly becomes null - due to object deletion, for example.
|
||||
Of course, you can also check the variables inside process() proc to prevent runtime errors.
|
||||
|
||||
Data storage vars:
|
||||
|
||||
result - stores the value returned by process() proc
|
||||
*/
|
||||
|
||||
/datum/global_iterator
|
||||
var/control_switch = 0
|
||||
var/delay = 10
|
||||
var/list/arg_list = new
|
||||
var/last_exec = null
|
||||
var/check_for_null = 1
|
||||
var/forbid_garbage = 0
|
||||
var/result
|
||||
var/state = 0
|
||||
|
||||
New(list/arguments=null,autostart=1)
|
||||
delay = delay>0?(delay):1
|
||||
if(forbid_garbage) //prevents garbage collection with tag != null
|
||||
tag = "\ref[src]"
|
||||
set_process_args(arguments)
|
||||
if(autostart)
|
||||
start()
|
||||
return
|
||||
|
||||
proc/main()
|
||||
state = 1
|
||||
while(src && control_switch)
|
||||
last_exec = world.timeofday
|
||||
if(check_for_null && has_null_args())
|
||||
stop()
|
||||
return 0
|
||||
result = process(arglist(arg_list))
|
||||
for(var/sleep_time=delay;sleep_time>0;sleep_time--) //uhh, this is ugly. But I see no other way to terminate sleeping proc. Such disgrace.
|
||||
if(!control_switch)
|
||||
return 0
|
||||
sleep(1)
|
||||
return 0
|
||||
|
||||
proc/start(list/arguments=null)
|
||||
if(active())
|
||||
return
|
||||
if(arguments)
|
||||
if(!set_process_args(arguments))
|
||||
return 0
|
||||
if(!state_check()) //the main loop is sleeping, wait for it to terminate.
|
||||
return
|
||||
control_switch = 1
|
||||
spawn()
|
||||
state = main()
|
||||
return 1
|
||||
|
||||
proc/stop()
|
||||
if(!active())
|
||||
return
|
||||
control_switch = 0
|
||||
spawn(-1) //report termination error but don't wait for state_check().
|
||||
state_check()
|
||||
return 1
|
||||
|
||||
proc/state_check()
|
||||
var/lag = 0
|
||||
while(state)
|
||||
sleep(1)
|
||||
if(++lag>10)
|
||||
CRASH("The global_iterator loop \ref[src] failed to terminate in designated timeframe. This may be caused by server lagging.")
|
||||
return 1
|
||||
|
||||
proc/process()
|
||||
return
|
||||
|
||||
proc/active()
|
||||
return control_switch
|
||||
|
||||
proc/has_null_args()
|
||||
if(null in arg_list)
|
||||
return 1
|
||||
return 0
|
||||
|
||||
|
||||
proc/set_delay(new_delay)
|
||||
if(isnum(new_delay))
|
||||
delay = max(1, round(new_delay))
|
||||
return 1
|
||||
else
|
||||
return 0
|
||||
|
||||
proc/get_last_exec_time()
|
||||
return (last_exec||0)
|
||||
|
||||
proc/get_last_exec_time_as_text()
|
||||
return (time2text(last_exec)||"Wasn't executed yet")
|
||||
|
||||
proc/set_process_args(list/arguments)
|
||||
if(arguments && istype(arguments, /list) && arguments.len)
|
||||
arg_list = arguments
|
||||
return 1
|
||||
else
|
||||
// world << "\red Invalid arguments supplied for [src.type], ref = \ref[src]"
|
||||
return 0
|
||||
|
||||
proc/toggle_null_checks()
|
||||
check_for_null = !check_for_null
|
||||
return check_for_null
|
||||
|
||||
proc/toggle()
|
||||
if(!stop())
|
||||
start()
|
||||
return active()
|
||||
|
||||
|
||||
@@ -0,0 +1,185 @@
|
||||
//wrapper
|
||||
/proc/do_teleport(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
|
||||
new /datum/teleport/instant/science(arglist(args))
|
||||
return
|
||||
|
||||
/datum/teleport
|
||||
var/atom/movable/teleatom //atom to teleport
|
||||
var/atom/destination //destination to teleport to
|
||||
var/precision = 0 //teleport precision
|
||||
var/datum/effect/effect/system/effectin //effect to show right before teleportation
|
||||
var/datum/effect/effect/system/effectout //effect to show right after teleportation
|
||||
var/soundin //soundfile to play before teleportation
|
||||
var/soundout //soundfile to play after teleportation
|
||||
var/force_teleport = 1 //if false, teleport will use Move() proc (dense objects will prevent teleportation)
|
||||
|
||||
|
||||
New(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
|
||||
..()
|
||||
if(!Init(arglist(args)))
|
||||
return 0
|
||||
return 1
|
||||
|
||||
proc/Init(ateleatom,adestination,aprecision,afteleport,aeffectin,aeffectout,asoundin,asoundout)
|
||||
if(!setTeleatom(ateleatom))
|
||||
return 0
|
||||
if(!setDestination(adestination))
|
||||
return 0
|
||||
if(!setPrecision(aprecision))
|
||||
return 0
|
||||
setEffects(aeffectin,aeffectout)
|
||||
setForceTeleport(afteleport)
|
||||
setSounds(asoundin,asoundout)
|
||||
return 1
|
||||
|
||||
//must succeed
|
||||
proc/setPrecision(aprecision)
|
||||
if(isnum(aprecision))
|
||||
precision = aprecision
|
||||
return 1
|
||||
return 0
|
||||
|
||||
//must succeed
|
||||
proc/setDestination(atom/adestination)
|
||||
if(istype(adestination))
|
||||
destination = adestination
|
||||
return 1
|
||||
return 0
|
||||
|
||||
//must succeed in most cases
|
||||
proc/setTeleatom(atom/movable/ateleatom)
|
||||
if(istype(ateleatom, /obj/effect) && !istype(ateleatom, /obj/effect/dummy/chameleon))
|
||||
del(ateleatom)
|
||||
return 0
|
||||
if(istype(ateleatom))
|
||||
teleatom = ateleatom
|
||||
return 1
|
||||
return 0
|
||||
|
||||
//custom effects must be properly set up first for instant-type teleports
|
||||
//optional
|
||||
proc/setEffects(datum/effect/effect/system/aeffectin=null,datum/effect/effect/system/aeffectout=null)
|
||||
effectin = istype(aeffectin) ? aeffectin : null
|
||||
effectout = istype(aeffectout) ? aeffectout : null
|
||||
return 1
|
||||
|
||||
//optional
|
||||
proc/setForceTeleport(afteleport)
|
||||
force_teleport = afteleport
|
||||
return 1
|
||||
|
||||
//optional
|
||||
proc/setSounds(asoundin=null,asoundout=null)
|
||||
soundin = isfile(asoundin) ? asoundin : null
|
||||
soundout = isfile(asoundout) ? asoundout : null
|
||||
return 1
|
||||
|
||||
//placeholder
|
||||
proc/teleportChecks()
|
||||
return 1
|
||||
|
||||
proc/playSpecials(atom/location,datum/effect/effect/system/effect,sound)
|
||||
if(location)
|
||||
if(effect)
|
||||
spawn(-1)
|
||||
src = null
|
||||
effect.attach(location)
|
||||
effect.start()
|
||||
if(sound)
|
||||
spawn(-1)
|
||||
src = null
|
||||
playsound(location,sound,60,1)
|
||||
return
|
||||
|
||||
//do the monkey dance
|
||||
proc/doTeleport()
|
||||
|
||||
var/turf/destturf
|
||||
var/turf/curturf = get_turf(teleatom)
|
||||
var/area/destarea = get_area(destination)
|
||||
if(precision)
|
||||
var/list/posturfs = circlerangeturfs(destination,precision)
|
||||
destturf = safepick(posturfs)
|
||||
else
|
||||
destturf = get_turf(destination)
|
||||
|
||||
if(!destturf || !curturf)
|
||||
return 0
|
||||
|
||||
playSpecials(curturf,effectin,soundin)
|
||||
|
||||
if(force_teleport)
|
||||
teleatom.forceMove(destturf)
|
||||
playSpecials(destturf,effectout,soundout)
|
||||
else
|
||||
if(teleatom.Move(destturf))
|
||||
playSpecials(destturf,effectout,soundout)
|
||||
|
||||
destarea.Entered(teleatom)
|
||||
|
||||
return 1
|
||||
|
||||
proc/teleport()
|
||||
if(teleportChecks())
|
||||
return doTeleport()
|
||||
return 0
|
||||
|
||||
/datum/teleport/instant //teleports when datum is created
|
||||
|
||||
New(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
|
||||
if(..())
|
||||
teleport()
|
||||
return
|
||||
|
||||
|
||||
/datum/teleport/instant/science
|
||||
|
||||
setEffects(datum/effect/effect/system/aeffectin,datum/effect/effect/system/aeffectout)
|
||||
if(!aeffectin || !aeffectout)
|
||||
var/datum/effect/effect/system/spark_spread/aeffect = new
|
||||
aeffect.set_up(5, 1, teleatom)
|
||||
effectin = effectin || aeffect
|
||||
effectout = effectout || aeffect
|
||||
return 1
|
||||
else
|
||||
return ..()
|
||||
|
||||
setPrecision(aprecision)
|
||||
..()
|
||||
if(istype(teleatom, /obj/item/weapon/storage/backpack/holding))
|
||||
precision = rand(1,100)
|
||||
|
||||
var/list/bagholding = teleatom.search_contents_for(/obj/item/weapon/storage/backpack/holding)
|
||||
if(bagholding.len)
|
||||
precision = max(rand(1,100)*bagholding.len,100)
|
||||
if(istype(teleatom, /mob/living))
|
||||
var/mob/living/MM = teleatom
|
||||
MM << "\red The Bluespace interface on your Bag of Holding interferes with the teleport!"
|
||||
return 1
|
||||
|
||||
teleportChecks()
|
||||
if(istype(teleatom, /obj/item/weapon/disk/nuclear)) // Don't let nuke disks get teleported --NeoFite
|
||||
teleatom.visible_message("\red <B>The [teleatom] bounces off of the portal!</B>")
|
||||
return 0
|
||||
|
||||
if(!isemptylist(teleatom.search_contents_for(/obj/item/weapon/disk/nuclear)))
|
||||
if(istype(teleatom, /mob/living))
|
||||
var/mob/living/MM = teleatom
|
||||
MM.visible_message("\red <B>The [MM] bounces off of the portal!</B>","\red Something you are carrying seems to be unable to pass through the portal. Better drop it if you want to go through.")
|
||||
else
|
||||
teleatom.visible_message("\red <B>The [teleatom] bounces off of the portal!</B>")
|
||||
return 0
|
||||
|
||||
if(destination.z == 2) //centcomm z-level
|
||||
if(istype(teleatom, /obj/mecha))
|
||||
var/obj/mecha/MM = teleatom
|
||||
MM.occupant << "\red <B>The mech would not survive the jump to a location so far away!</B>"
|
||||
return 0
|
||||
if(!isemptylist(teleatom.search_contents_for(/obj/item/weapon/storage/backpack/holding)))
|
||||
teleatom.visible_message("\red <B>The Bag of Holding bounces off of the portal!</B>")
|
||||
return 0
|
||||
|
||||
|
||||
if(destination.z > 7) //Away mission z-levels
|
||||
return 0
|
||||
return 1
|
||||
@@ -0,0 +1,60 @@
|
||||
/datum/topic_input
|
||||
var/href
|
||||
var/list/href_list
|
||||
|
||||
New(thref,list/thref_list)
|
||||
href = thref
|
||||
href_list = thref_list.Copy()
|
||||
return
|
||||
|
||||
proc/get(i)
|
||||
return listgetindex(href_list,i)
|
||||
|
||||
proc/getAndLocate(i)
|
||||
var/t = get(i)
|
||||
if(t)
|
||||
t = locate(t)
|
||||
return t || null
|
||||
|
||||
proc/getNum(i)
|
||||
var/t = get(i)
|
||||
if(t)
|
||||
t = text2num(t)
|
||||
return isnum(t) ? t : null
|
||||
|
||||
proc/getObj(i)
|
||||
var/t = getAndLocate(i)
|
||||
return isobj(t) ? t : null
|
||||
|
||||
proc/getMob(i)
|
||||
var/t = getAndLocate(i)
|
||||
return ismob(t) ? t : null
|
||||
|
||||
proc/getTurf(i)
|
||||
var/t = getAndLocate(i)
|
||||
return isturf(t) ? t : null
|
||||
|
||||
proc/getAtom(i)
|
||||
return getType(i,/atom)
|
||||
|
||||
proc/getArea(i)
|
||||
var/t = getAndLocate(i)
|
||||
return isarea(t) ? t : null
|
||||
|
||||
proc/getStr(i)//params should always be text, but...
|
||||
var/t = get(i)
|
||||
return istext(t) ? t : null
|
||||
|
||||
proc/getType(i,type)
|
||||
var/t = getAndLocate(i)
|
||||
return istype(t,type) ? t : null
|
||||
|
||||
proc/getPath(i)
|
||||
var/t = get(i)
|
||||
if(t)
|
||||
t = text2path(t)
|
||||
return ispath(t) ? t : null
|
||||
|
||||
proc/getList(i)
|
||||
var/t = getAndLocate(i)
|
||||
return islist(t) ? t : null
|
||||
Reference in New Issue
Block a user