29 g_sandbox_objects =
IL_NEW();
36 const float MAX_STORAGE_ATTACHMENTS = 16;
89 this.realowner =
NULL;
94 CSQCMODEL_AUTOUPDATE(
this);
124 _setmodel(e, e.model);
125 setsize(e, e.mins * e.scale, e.maxs * e.scale);
137 e.old_solid = e.solid;
138 e.old_movetype = e.move_movetype;
143 setattachment(e, parent, s);
151 IL_EACH(g_sandbox_objects, it.owner == e,
153 vector org = gettaginfo(it, 0);
154 setattachment(it, NULL,
"");
159 it.angles = e.angles;
161 it.solid = it.old_solid;
162 set_movetype(it, it.old_movetype);
163 it.takedamage = DAMAGE_AIM;
174 e.damageforcescale = 1;
192 print_to(
this,
"^1SANDBOX - WARNING: ^7You spawned an object, but lack a player UID. ^1Your objects are not secured and can be edited by any player!");
196 e.message =
strzone(strftime(
true,
"%d-%m-%Y %H:%M:%S"));
197 e.message2 =
strzone(strftime(
true,
"%d-%m-%Y %H:%M:%S"));
206 CSQCMODEL_AUTOINIT(e);
240 int slot, physics, solidity;
245 physics = it.move_movetype;
247 else if(it.owner == e)
251 solidity = it.old_solid;
252 physics = it.old_movetype;
253 gettaginfo(it.owner, it.tag_index);
263 port_string[slot] = strcat(port_string[slot],
"\"", gettaginfo_name,
"\" ");
265 port_string[slot] = strcat(port_string[slot],
"\"\" ");
272 port_string[slot] = strcat(port_string[slot], sprintf(
"\"%.9v\"", it.origin),
" ");
273 port_string[slot] = strcat(port_string[slot], sprintf(
"\"%.9v\"", it.angles),
" ");
277 port_string[slot] =
strcat(port_string[slot],
"\"", it.model,
"\" ");
278 port_string[slot] =
strcat(port_string[slot],
ftos(it.skin),
" ");
279 port_string[slot] =
strcat(port_string[slot],
ftos(it.alpha),
" ");
280 port_string[slot] =
strcat(port_string[slot], sprintf(
"\"%.9v\"", it.colormod),
" ");
281 port_string[slot] =
strcat(port_string[slot], sprintf(
"\"%.9v\"", it.glowmod),
" ");
282 port_string[slot] =
strcat(port_string[slot],
ftos(it.frame),
" ");
283 port_string[slot] =
strcat(port_string[slot],
ftos(it.scale),
" ");
284 port_string[slot] =
strcat(port_string[slot],
ftos(solidity),
" ");
285 port_string[slot] =
strcat(port_string[slot],
ftos(physics),
" ");
286 port_string[slot] =
strcat(port_string[slot],
ftos(it.damageforcescale),
" ");
288 port_string[slot] =
strcat(port_string[slot],
"\"", it.material,
"\" ");
290 port_string[slot] =
strcat(port_string[slot],
"\"\" ");
295 port_string[slot] =
strcat(port_string[slot],
"\"", it.crypto_idfp,
"\" ");
297 port_string[slot] =
strcat(port_string[slot],
"\"\" ");
298 port_string[slot] =
strcat(port_string[slot],
"\"", e.netname,
"\" ");
299 port_string[slot] =
strcat(port_string[slot],
"\"", e.message,
"\" ");
300 port_string[slot] =
strcat(port_string[slot],
"\"", e.message2,
"\" ");
306 for(
int j = 0; j <= MAX_STORAGE_ATTACHMENTS; ++j)
309 s =
strcat(s, port_string[j],
"; ");
325 for(i = 0; i < n; ++i)
329 for(i = 0; i < n; ++i)
331 #define SANDBOX_GETARG arg = argv(++argv_num); 383 for(i = 0; i <= MAX_STORAGE_ATTACHMENTS; ++i)
400 IL_EACH(g_sandbox_objects, !it.owner,
403 fputs(file_get, strcat(sandbox_ObjectPort_Save(it, true),
"\n"));
411 string file_read, file_name;
419 LOG_INFO(
"^3SANDBOX - SERVER: ^7could not find storage file ^3", file_name,
"^7, no objects were loaded");
425 file_read =
fgets(file_get);
439 for (i = 1; i <= 5; i++)
444 LOG_INFO(
"^3SANDBOX - SERVER: ^7successfully loaded storage file ^3", file_name);
458 if(cmd_name ==
"g_sandbox")
462 print_to(player,
"^2SANDBOX - INFO: ^7Sandbox mode is active, but in read-only mode. Sandbox commands cannot be used");
467 print_to(player,
"^2SANDBOX - INFO: ^7Sandbox mode is active. For usage information, type 'sandbox help'");
479 print_to(player,
"You can use the following sandbox commands:");
480 print_to(player,
"^7\"^2object_spawn ^3models/foo/bar.md3^7\" spawns a new object in front of the player, and gives it the specified model");
481 print_to(player,
"^7\"^2object_remove^7\" removes the object the player is looking at. Players can only remove their own objects");
482 print_to(player,
"^7\"^2object_duplicate ^3value^7\" duplicates the object, if the player has copying rights over the original");
483 print_to(player,
"^3copy value ^7- copies the properties of the object to the specified client cvar");
484 print_to(player,
"^3paste value ^7- spawns an object with the given properties. Properties or cvars must be specified as follows; eg1: \"0 1 2 ...\", eg2: \"$cl_cvar\"");
485 print_to(player,
"^7\"^2object_attach ^3property value^7\" attaches one object to another. Players can only attach their own objects");
486 print_to(player,
"^3get ^7- selects the object you are facing as the object to be attached");
487 print_to(player,
"^3set value ^7- attaches the previously selected object to the object you are facing, on the specified bone");
488 print_to(player,
"^3remove ^7- detaches all objects from the object you are facing");
489 print_to(player,
"^7\"^2object_edit ^3property value^7\" edits the given property of the object. Players can only edit their own objects");
490 print_to(player,
"^3skin value ^7- changes the skin of the object");
491 print_to(player,
"^3alpha value ^7- sets object transparency");
492 print_to(player,
"^3colormod \"value_x value_y value_z\" ^7- main object color");
493 print_to(player,
"^3glowmod \"value_x value_y value_z\" ^7- glow object color");
494 print_to(player,
"^3frame value ^7- object animation frame, for self-animated models");
495 print_to(player,
"^3scale value ^7- changes object scale. 0.5 is half size and 2 is double size");
496 print_to(player,
"^3solidity value ^7- object collisions, 0 = non-solid, 1 = solid");
497 print_to(player,
"^3physics value ^7- object physics, 0 = static, 1 = movable, 2 = physical");
498 print_to(player,
"^3force value ^7- amount of force applied to objects that are shot");
499 print_to(player,
"^3material value ^7- sets the material of the object. Default materials are: metal, stone, wood, flesh");
500 print_to(player,
"^7\"^2object_claim^7\" sets the player as the owner of the object, if he has the right to edit it");
501 print_to(player,
"^7\"^2object_info ^3value^7\" shows public information about the object");
502 print_to(player,
"^3object ^7- prints general information about the object, such as owner and creation / editing date");
503 print_to(player,
"^3mesh ^7- prints information about the object's mesh, including skeletal bones");
504 print_to(player,
"^3attachments ^7- prints information about the object's attachments");
505 print_to(player,
"^7The ^1drag object ^7key can be used to grab and carry objects. Players can only grab their own objects");
510 if(
time < player.object_flood)
512 print_to(player,
strcat(
"^1SANDBOX - WARNING: ^7Flood protection active. Please wait ^3",
ftos(player.object_flood -
time),
" ^7seconds beofore spawning another object"));
523 print_to(player,
"^1SANDBOX - WARNING: ^7Attempted to spawn an object without specifying a model. Please specify the path to your model file after the 'object_spawn' command");
528 print_to(player,
"^1SANDBOX - WARNING: ^7Attempted to spawn an object with a non-existent model. Make sure the path to your model file is correct");
533 _setmodel(e,
argv(2));
536 LOG_INFO(
"^3SANDBOX - SERVER: ^7", player.netname,
" spawned an object at origin ^3",
vtos(e.origin));
540 case "object_remove":
545 LOG_INFO(
"^3SANDBOX - SERVER: ^7", player.netname,
" removed an object at origin ^3",
vtos(e.origin));
550 print_to(player,
"^1SANDBOX - WARNING: ^7Object could not be removed. Make sure you are facing an object that you have edit rights over");
554 case "object_duplicate":
563 s = strreplace(
"\"",
"\\\"", s);
566 print_to(player,
"^2SANDBOX - INFO: ^7Object copied to clipboard");
569 print_to(player,
"^1SANDBOX - WARNING: ^7Object could not be copied. Make sure you are facing an object that you have copy rights over");
574 if(
time < player.object_flood)
576 print_to(player,
strcat(
"^1SANDBOX - WARNING: ^7Flood protection active. Please wait ^3",
ftos(player.object_flood -
time),
" ^7seconds beofore spawning another object"));
582 print_to(player,
"^1SANDBOX - WARNING: ^7No object in clipboard. You must copy an object before you can paste it");
592 print_to(player,
"^2SANDBOX - INFO: ^7Object pasted successfully");
594 LOG_INFO(
"^3SANDBOX - SERVER: ^7", player.netname,
" pasted an object at origin ^3",
vtos(e.origin));
600 case "object_attach":
608 player.object_attach = e;
609 print_to(player,
"^2SANDBOX - INFO: ^7Object selected for attachment");
612 print_to(player,
"^1SANDBOX - WARNING: ^7Object could not be selected for attachment. Make sure you are facing an object that you have edit rights over");
615 if(player.object_attach ==
NULL)
617 print_to(player,
"^1SANDBOX - WARNING: ^7No object selected for attachment. Please select an object to be attached first.");
626 player.object_attach =
NULL;
627 print_to(player,
"^2SANDBOX - INFO: ^7Object attached successfully");
629 LOG_INFO(
"^3SANDBOX - SERVER: ^7", player.netname,
" attached objects at origin ^3",
vtos(e.origin));
632 print_to(player,
"^1SANDBOX - WARNING: ^7Object could not be attached to the parent. Make sure you are facing an object that you have edit rights over");
640 print_to(player,
"^2SANDBOX - INFO: ^7Child objects detached successfully");
642 LOG_INFO(
"^3SANDBOX - SERVER: ^7", player.netname,
" detached objects at origin ^3",
vtos(e.origin));
645 print_to(player,
"^1SANDBOX - WARNING: ^7Child objects could not be detached. Make sure you are facing an object that you have edit rights over");
654 print_to(player,
"^1SANDBOX - WARNING: ^7Too few parameters. You must specify a property to edit");
716 for (j = 1; j <= 5; j++)
724 print_to(player,
"^1SANDBOX - WARNING: ^7Invalid object property. For usage information, type 'sandbox help'");
729 strcpy(e.message2, strftime(
true,
"%d-%m-%Y %H:%M:%S"));
732 LOG_INFO(
"^3SANDBOX - SERVER: ^7", player.netname,
" edited property ^3",
argv(2),
" ^7of an object at origin ^3",
vtos(e.origin));
736 print_to(player,
"^1SANDBOX - WARNING: ^7Object could not be edited. Make sure you are facing an object that you have edit rights over");
742 if(player.crypto_idfp ==
"")
744 print_to(player,
"^1SANDBOX - WARNING: ^7You do not have a player UID, and cannot claim objects");
753 if(e.netname != player.netname)
755 strcpy(e.netname, player.netname);
756 print_to(player,
"^2SANDBOX - INFO: ^7Object owner name updated");
759 if(e.crypto_idfp == player.crypto_idfp)
761 print_to(player,
"^2SANDBOX - INFO: ^7Object is already yours, nothing to claim");
765 strcpy(e.crypto_idfp, player.crypto_idfp);
767 print_to(player,
"^2SANDBOX - INFO: ^7Object claimed successfully");
769 print_to(player,
"^1SANDBOX - WARNING: ^7Object could not be claimed. Make sure you are facing an object that you have edit rights over");
781 print_to(player,
strcat(
"^2SANDBOX - INFO: ^7Object is owned by \"^7", e.netname,
"^7\", created \"^3", e.message,
"^7\", last edited \"^3", e.message2,
"^7\""));
787 print_to(player,
strcat(
"^2SANDBOX - INFO: ^7Object mesh is \"^3", e.model,
"^7\" at animation frame ^3",
ftos(e.frame),
" ^7containing the following tags: ", s));
793 IL_EACH(g_sandbox_objects, it.owner == e,
796 gettaginfo(e, it.tag_index);
797 s = strcat(s,
"^1attachment ", ftos(j),
"^7 has mesh \"^3", it.model,
"^7\" at animation frame ^3", ftos(it.frame));
798 s = strcat(s,
"^7 and is attached to bone \"^5", gettaginfo_name,
"^7\", ");
801 print_to(player,
strcat(
"^2SANDBOX - INFO: ^7Object contains the following ^1",
ftos(j),
"^7 attachment(s): ", s));
803 print_to(player,
"^2SANDBOX - INFO: ^7Object contains no attachments");
807 print_to(player,
"^1SANDBOX - WARNING: ^7No information could be found. Make sure you are facing an object");
812 print_to(player,
"Invalid command. For usage information, type 'sandbox help'");
#define IL_EACH(this, cond, body)
void sandbox_Database_Save()
float autocvar_g_sandbox_object_scale_max
string autocvar_g_sandbox
#define REGISTER_MUTATOR(id, dependence)
float autocvar_g_sandbox_object_scale_min
const float MOVETYPE_PHYSICS
void sandbox_ObjectAttach_Set(entity e, entity parent, string s)
float autocvar_g_sandbox_editor_flood
entity sandbox_ObjectSpawn(entity this, float database)
IntrusiveList g_sandbox_objects
#define FOREACH_CLIENT(cond, body)
float autocvar_g_sandbox_storage_autosave
entity sandbox_ObjectPort_Load(entity this, string s, float database)
void print_to(entity to, string input)
limitations: NULL cannot be present elements can only be present once a maximum of IL_MAX lists can e...
void sandbox_Database_Load()
int autocvar_g_sandbox_editor_free
MUTATOR_HOOKFUNCTION(sandbox, SV_ParseClientCommand)
float autocvar_g_sandbox_object_material_velocity_min
void sandbox_ObjectEdit_Scale(entity e, float f)
void sandbox_ObjectFunction_Touch(entity this, entity toucher)
#define IS_REAL_CLIENT(v)
entity sandbox_ObjectEdit_Get(entity this, float permissions)
void sandbox_ObjectAttach_Remove(entity e)
string sandbox_ObjectPort_Save(entity e, bool database)
void sandbox_ObjectRemove(entity e)
void SV_ParseClientCommand(entity this, string command)
ERASEABLE entity IL_PUSH(IntrusiveList this, entity it)
Push to tail.
float autocvar_g_sandbox_editor_distance_edit
int autocvar_g_sandbox_editor_maxobjects
spree_cen s1 spree_cen s1 spree_cen s1 spree_cen s1 spree_cen s1 spree_cen s1 spree_cen s1 f1 s1 strcat(_("Level %s: "), "^BG%s\3\, _("^BGPress ^F2%s^BG to enter the game"))
bool autocvar_g_sandbox_storage_autoload
string autocvar_g_sandbox_storage_name
#define MUTATOR_RETURNVALUE
int autocvar_g_sandbox_info
#define vdist(v, cmp, f)
Vector distance comparison, avoids sqrt()
void WarpZone_TraceLine(vector org, vector end, float nomonsters, entity forent)
#define _sound(e, c, s, v, a)
bool autocvar_g_sandbox_readonly
const float SOLID_TRIGGER
#define tokenizebyseparator
string port_string[MAX_STORAGE_ATTACHMENTS]
void crosshair_trace_plusvisibletriggers(entity pl)
float autocvar_g_sandbox_object_material_velocity_factor
ERASEABLE bool fexists(string f)
void sandbox_ObjectFunction_Think(entity this)
float autocvar_g_sandbox_editor_distance_spawn
void set_movetype(entity this, int mt)
ERASEABLE bool expr_evaluate(string s)
Evaluate an expression of the form: [+ | -]? [var[op]val | [op]var | val | var] ...