#pragma once #include #define TOPICS(X) \ X(NEW(FreetextSource), _("Guide"), "gametype_tdm") \ X(NEW(GametypeSource), _("Gametypes"), "gametype_dm") \ X(NEW(WeaponSource), _("Weapons"), "gametype_ka") \ X(NEW(ItemSource), _("Items"), "gametype_kh") \ X(NEW(BuffSource), _("Buffs"), "gametype_dom") \ X(NEW(NadeSource), _("Nades"), "gametype_ft") \ X(NEW(MonsterSource), _("Monsters"), "gametype_lms") \ X(NEW(VehicleSource), _("Vehicles"), "gametype_rc") \ X(NEW(TurretSource), _("Turrets"), "gametype_as") \ X(NEW(MutatorSource), _("Mutators"), "gametype_nb") \ X(NEW(MapSource), _("Maps"), "gametype_ctf") \ if (cvar("developer")) X(NEW(DebugSource), _("Debug"), "gametype_ons") \ /**/ CLASS(TopicSource, DataSource) METHOD(TopicSource, getEntry, entity(TopicSource this, int i, void(string, string) returns)) { int idx = 0; #define TOPIC(src, name, icon) if (idx++ == i) { if (returns) returns(name, icon); return DataSource_true; } TOPICS(TOPIC); #undef TOPIC if (returns) returns("undefined", "undefined"); return DataSource_false; } METHOD(TopicSource, reload, int(TopicSource this, string filter)) { int n = 0; #define TOPIC(src, name, icon) n++; TOPICS(TOPIC); #undef TOPIC return n; } ENDCLASS(TopicSource) CLASS(DebugSource, DataSource) .entity nextdebug; entity find_debug() { entity head = NULL, tail = NULL; for (entity it = NULL; (it = nextent(it)); ) { if (!it.instanceOfObject) continue; if (it.instanceOfGameItem) continue; if (it.instanceOfAnimHost) continue; if (it.instanceOfDataSource) continue; if (it.classname == "Object") continue; if (it.classname == "vtbl") continue; if (!tail) { tail = head = it; } else { tail.nextdebug = it; tail = it; } } return head; } string DebugSource_activeFilter = ""; METHOD(DebugSource, getEntry, entity(DebugSource this, int i, void(string, string) returns)) { int idx = 0; entity e; for (e = find_debug(); e; e = e.nextdebug) { if (strstrofs(sprintf("entity %i", e), DebugSource_activeFilter, 0) < 0) continue; if (idx++ == i) break; } if (returns) e.display(e, returns); return e; } METHOD(DebugSource, reload, int(DebugSource this, string filter)) { DebugSource_activeFilter = filter; int idx = 0; entity e; for (e = find_debug(); e; e = e.nextdebug) { if (strstrofs(sprintf("entity %i", e), DebugSource_activeFilter, 0) < 0) continue; idx++; } return idx; } ENDCLASS(DebugSource) #define REGISTRY_SOURCE(id, arr) \ CLASS(id, DataSource) \ METHOD(id, getEntry, entity(id this, int i, void(string, string) returns)) { \ entity e = _R_GET(_##arr, i); \ if (returns) e.display(e, returns); \ return e; \ } \ METHOD(id, reload, int(id this, string filter)) { return arr##_COUNT; } \ ENDCLASS(id) #include "pages.qh" REGISTRY_SOURCE(FreetextSource, GuidePages) #include REGISTRY_SOURCE(GametypeSource, Gametypes) #include REGISTRY_SOURCE(ItemSource, Items) #include REGISTRY_SOURCE(BuffSource, Buffs) #include REGISTRY_SOURCE(NadeSource, Nades) #include REGISTRY_SOURCE(WeaponSource, Weapons) #include REGISTRY_SOURCE(MonsterSource, Monsters) #include REGISTRY_SOURCE(VehicleSource, Vehicles) #include REGISTRY_SOURCE(TurretSource, Turrets) #include REGISTRY_SOURCE(MutatorSource, Mutators) CLASS(MapSource, DataSource) METHOD(MapSource, getEntry, entity(MapSource this, int i, void(string, string) returns)) { if (!MapInfo_Get_ByID(i)) return DataSource_false; string path = strcat("/maps/", MapInfo_Map_bspname); string img = draw_PictureSize(path) ? path : "nopreview_map"; if (returns) returns(MapInfo_Map_titlestring, img); MapInfo_ClearTemps(); return DataSource_true; } METHOD(MapSource, indexOf, int(MapSource this, string s)) { MapInfo_FindName(s); return MapInfo_FindName_firstResult; } METHOD(MapSource, reload, int(MapSource this, string s)) { _MapInfo_FilterGametype(MAPINFO_TYPE_ALL, 0, 0, 0, 0); if (s) MapInfo_FilterString(s); return MapInfo_count; } METHOD(MapSource, destroy, void(MapSource this)) { MapInfo_Shutdown(); } ENDCLASS(MapSource) #include "topics.qh" #include "entries.qh" #include "description.qh" #include CLASS(XonoticGuideTab, XonoticTab) ATTRIB(XonoticGuideTab, rows, float, 21); ATTRIB(XonoticGuideTab, columns, float, 6); ATTRIB(XonoticGuideTab, intendedWidth, float, 1); METHOD(XonoticGuideTab, fill, void(entity)); METHOD(XonoticGuideTab, topicChangeNotify, void(entity, entity)); METHOD(XonoticGuideTab, entryChangeNotify, void(entity, entity)); ATTRIB(XonoticGuideTab, topicList, entity, NEW(XonoticTopicList, NEW(TopicSource))); ATTRIB(XonoticGuideTab, entryList, entity, NEW(XonoticEntryList, NULL)); ATTRIB(XonoticGuideTab, descriptionPane, entity, NEW(XonoticGuideDescription)); INIT(XonoticGuideTab) { this.configureDialog(this); } ENDCLASS(XonoticGuideTab)