summary refs log tree commit diff stats
path: root/src/entityfactory.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/entityfactory.cpp')
-rw-r--r--src/entityfactory.cpp101
1 files changed, 101 insertions, 0 deletions
diff --git a/src/entityfactory.cpp b/src/entityfactory.cpp new file mode 100644 index 0000000..acf9b8e --- /dev/null +++ b/src/entityfactory.cpp
@@ -0,0 +1,101 @@
1#include "entityfactory.h"
2#include <libxml/parser.h>
3#include "components.h"
4#include "muxer.h"
5#include <cstdio>
6
7struct EntityData {
8 char* sprite;
9 char* action;
10 bool hasPhysics;
11 int width;
12 int height;
13};
14
15static std::map<std::string, EntityData> factories;
16
17std::shared_ptr<Entity> EntityFactory::createNamedEntity(const std::string name, const Map& map)
18{
19 auto it = factories.find(name);
20 EntityData data = factories[name];
21 if (it == factories.end())
22 {
23 xmlDocPtr doc = xmlParseFile(("../entities/" + name + ".xml").c_str());
24 if (doc == nullptr)
25 {
26 fprintf(stderr, "Error reading entity %s\n", name.c_str());
27 exit(-1);
28 }
29
30 xmlNodePtr top = xmlDocGetRootElement(doc);
31 if (top == nullptr)
32 {
33 fprintf(stderr, "Empty entity %s\n", name.c_str());
34 exit(-1);
35 }
36
37 if (xmlStrcmp(top->name, (const xmlChar*) "entity-def"))
38 {
39 fprintf(stderr, "Invalid entity definition %s\n", name.c_str());
40 exit(-1);
41 }
42
43 for (xmlNodePtr node = top->xmlChildrenNode; node != NULL; node = node->next)
44 {
45 if (!xmlStrcmp(node->name, (const xmlChar*) "sprite"))
46 {
47 xmlChar* key = xmlNodeListGetString(doc, node->xmlChildrenNode, 1);
48 data.sprite = (char*) calloc(xmlStrlen(key)+1, sizeof(char));
49 strcpy(data.sprite, (char*) key);
50 xmlFree(key);
51 } else if (!xmlStrcmp(node->name, (const xmlChar*) "action"))
52 {
53 xmlChar* key = xmlNodeListGetString(doc, node->xmlChildrenNode, 1);
54 data.action = (char*) calloc(xmlStrlen(key)+1, sizeof(char));
55 strcpy(data.action, (char*) key);
56 xmlFree(key);
57 } else if (!xmlStrcmp(node->name, (const xmlChar*) "size"))
58 {
59 xmlChar* key = xmlNodeListGetString(doc, node->xmlChildrenNode, 1);
60 data.hasPhysics = true;
61 sscanf((char*) key, "%d,%d", &(data.width), &(data.height));
62 xmlFree(key);
63 }
64 }
65
66 xmlFreeDoc(doc);
67
68 factories[name] = data;
69 }
70
71 auto entity = std::make_shared<Entity>();
72
73 if (data.sprite)
74 {
75 auto component = std::make_shared<StaticImageComponent>(data.sprite);
76 entity->addComponent(component);
77 }
78
79 if (data.action)
80 {
81 if (!strcmp(data.action, "save"))
82 {
83 auto component = std::make_shared<SimpleColliderComponent>([&] (Game& game, Entity& collider) {
84 playSound("../res/Pickup_Coin23.wav", 0.25);
85
86 game.saveGame(map, collider.position);
87 });
88 entity->addComponent(component);
89 }
90 }
91
92 if (data.hasPhysics)
93 {
94 auto component = std::make_shared<PhysicsBodyComponent>();
95 entity->addComponent(component);
96
97 entity->size = std::make_pair(data.width, data.height);
98 }
99
100 return entity;
101}