R Soul on 7/4/2024 at 20:11
I've just been trying to write a script that, among other things, changes the colours of 'bitmap disks' of a particle effect. I thought the data type of the value would be a vector with r, g, b values. Turns out it's a string. Thought I'd post this in case anyone else gets puzzled by the same situation.
e.g, to set the first bitmap disk colour to blue:
Code:
class ParticleColour extends SqRootScript
{
function OnTurnOn()
{
SetProperty("ParticleGroup", "bm-disk rgb" , "0, 0, 255");
}
}
edit: inserting the word 'color' in case Americans do a search!
ZylonBane on 14/4/2024 at 23:53
One of the annoying shortcomings of Dark's script API is that it doesn't expose access to the object query engines that native code can use. This makes it near-impossible for Squirrel to perform global operations on objects that haven't already been helpfully set up with names or links. Or so I thought...
Turns out, you can get pretty darn close to arbitrary global object queries by using archetypes, which implement inheritance to their concretes as hidden metaproperty links, which scripts CAN access. I've written this function to demonstrate:
Code:
function GetConcretes(archetype, filter = null, arg = null) {
local obj, lnk;
local objList = [];
foreach (lnk in Link.GetAll("~MetaProp", archetype)) {
obj = LinkDest(lnk);
if (obj < 0) {
objList.extend(GetConcretes(obj, filter, arg));
}
else if (filter == null || (arg == null ? filter(obj) : filter(obj, arg))) {
objList.push(obj);
}
}
return objList;
}
Normally this would be embedded in a library class so all scripts could access it.
So using this function, you could for example write this to get a list of every patrol point in the entire mission.
Code:
local trolList = lib.GetConcretes("TrolPt");
Or if you want a list of every human guard, but only the living ones, you can pass in a filter function:
Code:
local gList = lib.GetConcretes("guard", filterGuards);
function filterGuards(obj) {
return Property.Get(obj, "HitPoints") > 0;
}
Or using the more compact lambda syntax...
Code:
local gList = lib.GetConcretes("guard", @(obj) Property.Get(obj, "HitPoints") > 0);
Note that "self" isn't preserved in functions called in other classes, so if the filter function needs it, or any other dynamic data, it can be passed in as an optional third argument.