p.s. Sorry if this is in the wrong forum, I suppose it's more of a tutorials&snippets+design philosophy+feature request hybrid post (see wat i did there?).
Overview:
The basic idea is to add customizable alternatives to the way vars and procs are accessed that take into account a list of parents. Also, functions are added to handle the inheritance process.
Issues:
- No functionality resembling parent calls, no chain of execution control other than the 'halt' var.
[Download Demo]
// stuff for caching datums
var/cache[]
proc/cache(a,b,list/list=cache)
if(a)
if(b)
if(!list)
cache=list()
list=cache
list[a]=b
if(list&&(a in list))
return list[a]
proc/temp(type)
// all-purpose cache wrapper for datums
if(type in cache)
return cache(type)
return cache(type,new type)
// the setup
datum
var/tmp
parents[]
params[]
halt
proc
param(p)
if(p in params) return params[p]
else if(p in vars) return vars[p]
set_param(p,v)
if(!params) params = list()
if(!(p in params)) params += p
params[p]=v
inherit(datum/d)
for(var/p in params)
d.set_param(p,param(p))
func(f,...)
var
_args[] = args.Copy(2)
chain[] = parents+src
_args.Insert(1,src)
halt = null
for(var/d in chain)
if(hascall(d,f))
.=call(d,f)(arglist(_args))
if(halt) return
add_parent(p)
if(!parents) parents = list()
var/datum/d
if(ispath(p))
d = temp(p)
parents += d
d.inherit(src)
take_parent(p)
p = is_type(p)
if(p)
parents -= p
if(parents.len<1) parents=null
is_type(p)
return locate(p) in parents
New()
.=..()
for(var/p in parents)
if(ispath(p))
add_parent(p)
parents -= p
// some examples
combatant
params = list("hp" = 10)
inherit(datum/d)
.=..()
if(istype(d,/mob))
d:verbs += /combatant/proc/attack
proc
attack()
var/turf/t = get_step(src,src:dir)
for(var/atom/a in t)
if(a.is_type(/combatant))
a.func("damage",1,src)
damage(datum/ref,dmg,trg)
ref.set_param("hp",ref.param("hp")-dmg)
//oview(ref) << "[ref] is hurt by [trg] for [dmg] damage."
if(ref.param("hp") < 1)
ref.func("die",trg)
die(datum/ref,trg)
//oview(ref) << "[ref] was slain by [trg]!"
hostile
inherit(datum/d)
.=..()
if(istype(d,/atom/movable))
var/atom/movable/a = d
spawn while(a)
var/mob/m = locate(/mob) in oview(a)
if(m)
if(get_dist(m,a)>1) step_to(a,m)
else m.func("damage",1,a)
sleep(2)
item
inherit(datum/d)
.=..()
d:verbs += /item/proc/get
d:verbs += /item/proc/drop
proc
get()
set src in oview(1)
src:Move(usr)
drop()
set src in usr
src:Move(usr.loc)
tree //murderous trees
parent_type = /obj
density = 1
parents = list(/combatant,/hostile)
proc/die()
new .wood (loc)
del src
wood
parent_type = /obj
parents = list(/item)
icon = 'wood.dmi'
mob
parents = list(/combatant)