]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/commitdiff
Cleanup OO macros
authorTimePath <andrew.hardaker1995@gmail.com>
Thu, 13 Aug 2015 08:13:53 +0000 (18:13 +1000)
committerTimePath <andrew.hardaker1995@gmail.com>
Thu, 13 Aug 2015 08:27:01 +0000 (18:27 +1000)
qcsrc/client/progs.src
qcsrc/common/oo.qh
qcsrc/common/registry.qh
qcsrc/common/util-post.qh [new file with mode: 0644]
qcsrc/common/util-pre.qh
qcsrc/dpdefs/csprogsdefs.qh
qcsrc/dpdefs/menudefs.qh
qcsrc/dpdefs/progsdefs.qh
qcsrc/menu/progs.src
qcsrc/server/progs.src

index 94c92a54c16553e270e7f972591a9136c8071a62..d161c6dfc60b09ff502b2cfa4bb24c313ade789d 100644 (file)
@@ -2,6 +2,7 @@
 
 ../common/util-pre.qh
 ../dpdefs/csprogsdefs.qh
+../common/util-post.qh
 
 announcer.qc
 bgmscript.qc
index 63b17089e48c0a8d080e30b797f46b689fd4385f..b2b8b0ad29305ef962c5c01c270d5628c10fb095 100644 (file)
@@ -1,71 +1,99 @@
 #ifndef OO_H
 #define OO_H
 
+#include "registry.qh"
+
 #ifdef MENUQC
-       #define NULL (null_entity)
+    #define NULL (null_entity)
 #else
-       #define NULL (world)
+    #define NULL (world)
 #endif
 
 .string classname;
-.string vtblname;
-.entity vtblbase;
-entity spawnVtbl(entity this, entity base)
-{
-       entity vtbl = spawn();
-       copyentity(this, vtbl);
-       vtbl.vtblname = vtbl.classname;
-       vtbl.classname = "vtbl";
-       vtbl.vtblbase = base ? base : vtbl; // Top level objects use vtbl as base
-       return vtbl;
+/** Location entity was spawned from in source */
+.string sourceLocFile;
+.int sourceLocLine;
+entity _spawn();
+entity __spawn(string _classname, string _sourceFile, int _sourceLine) {
+    entity this = _spawn();
+    this.classname = _classname;
+    this.sourceLocFile = _sourceFile;
+    this.sourceLocLine = _sourceLine;
+    return this;
 }
 
-entity Object_vtbl;
-entity spawnObject(entity this, entity)
-{
-       this = spawn();
-       this.classname = "Object";
-       if (!Object_vtbl) Object_vtbl = spawnVtbl(this, NULL);
-       return this;
-}
+#define entityclass(...) OVERLOAD(entityclass, __VA_ARGS__)
+#define entityclass_1(name) entityclass_2(name, Object)
+#ifndef QCC_SUPPORT_ENTITYCLASS
+    #define entityclass_2(name, base) typedef entity name
+    #define class(name)
+    #define new(class) __spawn(#class, __FILE__, __LINE__)
+#else
+    #define entityclass_2(name, base) entityclass name : base {}
+    #define class(name) [[class(name)]]
+    #define new(class) ((class) __spawn(#class, __FILE__, __LINE__))
+#endif
 
-// Classes have a `spawn##cname(entity, entity)` constructor
-// The parameters are used as locals for [[accumulate]]
+// Classes have a `spawn##cname(entity)` constructor
+// The parameter is used across [[accumulate]] functions
 
 // Macro to hide this implementation detail
-#define NEW(cname) (spawn##cname(NULL, NULL))
+#define NEW(cname) (spawn##cname(new(cname)))
 
-#define CLASS(cname, base)                                                     \
-entity spawn##cname(entity this, entity basevtbl) {                            \
-    this = NEW(base); basevtbl = base##_vtbl;                                  \
-}
+.string vtblname;
+.entity vtblbase;
 
-#define METHOD(cname, name, prototype)                                         \
-prototype cname##_##name;                                                      \
-.prototype name;                                                               \
-[[accumulate]] entity spawn##cname(entity this, entity basevtbl) {             \
-    this.name = cname##_##name;                                                \
-}
+#define VTBL(cname, base) \
+    entity cname##_vtbl; \
+    STATIC_INIT(cname##_vtbl) { \
+        entity e = NEW(cname); \
+        e.vtblname = #cname; \
+        e.classname = "vtbl"; \
+        /* Top level objects refer to themselves */ \
+        e.vtblbase = base ? base : e; \
+        cname##_vtbl = e; \
+    }
 
-#define ATTRIB(cname, name, type, val)                                         \
-.type name;                                                                    \
-[[accumulate]] entity spawn##cname(entity this, entity basevtbl) {             \
-    this.name = val;                                                           \
-}
+#define INIT_STATIC(cname) [[accumulate]] entity spawn##cname(entity this)
+#define INIT(cname) [[accumulate]] void spawn##cname##_init(entity this)
 
-#define ATTRIBARRAY(cname, name, type, cnt)                                    \
-.type name[cnt];
-
-#define ENDCLASS(cname)                                                        \
-.bool instanceOf##cname;                                                       \
-entity cname##_vtbl;                                                           \
-[[accumulate]] [[last]] entity spawn##cname(entity this, entity basevtbl) {    \
-    this.instanceOf##cname = true;                                             \
-    this.classname = #cname;                                                   \
-    if (!cname##_vtbl) cname##_vtbl = spawnVtbl(this, basevtbl);               \
-    return this;                                                               \
-}
+#define CLASS(cname, base)                  \
+    entityclass(cname, base);               \
+    class(cname) .bool instanceOf##cname;   \
+    INIT(cname) { }                         \
+    INIT_STATIC(cname);                     \
+    VTBL(cname, base##_vtbl)                \
+    INIT_STATIC(cname) {                    \
+        if (cname##_vtbl) {                 \
+            copyentity(cname##_vtbl, this); \
+            spawn##cname##_init(this);      \
+            return this;                    \
+        }                                   \
+        spawn##base(this);                  \
+        this.instanceOf##cname = true;      \
+    }
+
+#define METHOD(cname, name, prototype)      \
+    class(cname) .prototype name;           \
+    prototype cname##_##name;               \
+    INIT_STATIC(cname) { this.name = cname##_##name; }
+
+#define ATTRIB(cname, name, type, val)      \
+    class(cname) .type name;                \
+    INIT(cname) { this.name = val; }
+
+#define ATTRIBARRAY(cname, name, type, cnt) \
+    class(cname) .type name[cnt];
+
+#define ENDCLASS(cname) \
+    [[last]] INIT_STATIC(cname) { return this; }
 
 #define SUPER(cname) (cname##_vtbl.vtblbase)
 
+#define spawnNULL(e)
+#define NULL_vtbl NULL
+
+CLASS(Object, NULL)
+ENDCLASS(Object)
+
 #endif
index 4c24b491d9b33661bf562a333009dc1d89db5f30..0087c1bf71b77b69cf3513fcb0da62aa42017fed 100644 (file)
@@ -1,6 +1,8 @@
 #ifndef REGISTRY_H
 #define REGISTRY_H
 
+#include "util.qh"
+
 #define REGISTER_INIT(ns, id) [[accumulate]] void Register_##ns##_##id##_init(entity this)
 
 #define REGISTER(initfunc, ns, array, counter, id, class, fld)  \
@@ -20,4 +22,9 @@ void __static_init() { }
 #define static_init() CALL_ACCUMULATED_FUNCTION(__static_init)
 #define REGISTER_REGISTRY(func) ACCUMULATE_FUNCTION(__static_init, func)
 
+#define STATIC_INIT(func) \
+    void _static_##func(); \
+    ACCUMULATE_FUNCTION(__static_init, _static_##func) \
+    void _static_##func()
+
 #endif
diff --git a/qcsrc/common/util-post.qh b/qcsrc/common/util-post.qh
new file mode 100644 (file)
index 0000000..6d1ab21
--- /dev/null
@@ -0,0 +1,8 @@
+#ifndef UTIL_POST_H
+#define UTIL_POST_H
+
+#define spawn() new(entity)
+
+#include "oo.qh"
+
+#endif
index 9d60ae0a9ae2797bfdaedea9632237e81554f564..e681998557388e4e4d262e8ec92402ca7f803377 100644 (file)
     const int false = 0;
 #endif
 
-#ifndef QCC_SUPPORT_ENTITYCLASS
-    #define entityclass(name) typedef entity name
-    #define class(name)
-    #define new(class) spawn()
-#else
-    #define entityclass(name) entityclass name {}
-    #define class(name) [[class(name)]]
-    #define new(class) ((class) spawn())
-#endif
-
 // Transitional aliases
 [[deprecated("use true")]] [[alias("true")]] const bool TRUE;
 [[deprecated("use false")]] [[alias("false")]] const bool FALSE;
index c4d8c54ce05c4b6b847a36f54d1d6672beda0379..b10ef09baf75fadba2367fb6f5225c8bcec58b90 100644 (file)
@@ -8,6 +8,8 @@
 #define TRUE _TRUE
 #define FALSE _FALSE
 
+#define spawn _spawn
+
 #include "upstream/csprogsdefs.qc"
 
 #undef true
@@ -15,6 +17,8 @@
 #undef TRUE
 #undef FALSE
 
+#undef spawn
+
 #pragma noref 0
 
 #endif
index dce99cde598cbba758d4c3cb36fdc3db325a66ba..7d4dcc6af589598f1fa5abd72f5f29c4dee8790e 100644 (file)
@@ -8,6 +8,8 @@
 #define TRUE _TRUE
 #define FALSE _FALSE
 
+#define spawn _spawn
+
 #include "upstream/menudefs.qc"
 
 #undef true
@@ -15,6 +17,8 @@
 #undef TRUE
 #undef FALSE
 
+#undef spawn
+
 int(string str, string sub, int startpos) _strstrofs = #221;
 #define strstrofs _strstrofs
 int(string str, int ofs) _str2chr = #222;
index bffacafddc59a928ac76441e89fe284579bb173a..c2440d3dabffba98aaf3a1324d321267a224dd46 100644 (file)
@@ -8,6 +8,8 @@
 #define TRUE _TRUE
 #define FALSE _FALSE
 
+#define spawn _spawn
+
 #include "upstream/progsdefs.qc"
 
 #undef true
@@ -15,6 +17,8 @@
 #undef TRUE
 #undef FALSE
 
+#undef spawn
+
 #pragma noref 0
 
 #endif
index 2315616d1701bfc29dbdbe8cc7c6ce04e8433092..a35fd484f37c1263172229728da7d2672520ee40 100644 (file)
@@ -3,6 +3,7 @@
 ../common/util-pre.qh
 ../dpdefs/menudefs.qh
 ../dpdefs/keycodes.qh
+../common/util-post.qh
 
 oo/classes.qc
 
index 2d110d2f9fe273f3b2fca89bd3c582da92ac391e..388d1b675486fd8e0d1e21fb5db53343a0534682 100644 (file)
@@ -5,6 +5,7 @@ sys-pre.qh
 ../dpdefs/progsdefs.qh
 ../dpdefs/dpextensions.qh
 sys-post.qh
+../common/util-post.qh
 
 anticheat.qc
 antilag.qc