Fully working map editor
This commit is contained in:
parent
e74bbbbbd2
commit
8f790e497a
12
main.cpp
12
main.cpp
@ -21,7 +21,7 @@ void ui_map();
|
|||||||
|
|
||||||
|
|
||||||
int main(int argc, char *argv[]) {
|
int main(int argc, char *argv[]) {
|
||||||
UI ui(sf::Vector2u(1200, 1000), "JackEditor");
|
UI ui(sf::Vector2u(1400, 1000), "JackEditor");
|
||||||
|
|
||||||
while (ui.Update()) {
|
while (ui.Update()) {
|
||||||
static bool demo_open = false;
|
static bool demo_open = false;
|
||||||
@ -37,8 +37,16 @@ int main(int argc, char *argv[]) {
|
|||||||
|
|
||||||
if (demo_open)
|
if (demo_open)
|
||||||
ig::ShowDemoWindow(&demo_open);
|
ig::ShowDemoWindow(&demo_open);
|
||||||
if (bundleOpen)
|
if (bundleOpen) {
|
||||||
|
ig::PushID(1);
|
||||||
ui_bundle();
|
ui_bundle();
|
||||||
|
ig::PopID();
|
||||||
|
}
|
||||||
|
if (mapOpen) {
|
||||||
|
ig::PushID(2);
|
||||||
|
ui_map();
|
||||||
|
ig::PopID();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
ui.Render();
|
ui.Render();
|
||||||
|
138
map.cpp
138
map.cpp
@ -2,11 +2,145 @@
|
|||||||
#include "gui/gui.hpp"
|
#include "gui/gui.hpp"
|
||||||
#include "gui/imgui/imgui.h"
|
#include "gui/imgui/imgui.h"
|
||||||
#include "gui/imgui/imgui_stdlib.h"
|
#include "gui/imgui/imgui_stdlib.h"
|
||||||
|
#include "ig001.hpp"
|
||||||
#include "map_types.hpp"
|
#include "map_types.hpp"
|
||||||
#include <set>
|
#include <cmath>
|
||||||
|
#include <cstdlib>
|
||||||
|
#include <cstring>
|
||||||
|
#include <list>
|
||||||
|
#include <sstream>
|
||||||
|
|
||||||
|
|
||||||
static std::set<EntityBase *> entities, to_delete;
|
static std::list<EntityBase *> entities;
|
||||||
|
static EntityBase *selected_entity = NULL;
|
||||||
|
static EntityBase *to_delete = NULL;
|
||||||
|
static Vec2 offset0(0, 0);
|
||||||
|
static double cutoff = 1500;
|
||||||
|
|
||||||
|
|
||||||
void ui_map() {
|
void ui_map() {
|
||||||
|
Vec2 newdelta(ig::GetMouseDragDelta(ImGuiMouseButton_Right));
|
||||||
|
Vec2 offset = offset0 + newdelta;
|
||||||
|
if (!ig::IsMouseDragging(ImGuiMouseButton_Right))
|
||||||
|
offset0 = offset0 + newdelta;
|
||||||
|
|
||||||
|
if (ig::Begin("Entities")) {
|
||||||
|
if (ig::BeginMenu("Load Entities from Text")) {
|
||||||
|
static std::string buf_code;
|
||||||
|
ig::InputTextMultiline("##Code", &buf_code, ImVec2(400, 300));
|
||||||
|
if (ig::Button("Load!")) {
|
||||||
|
for (EntityBase *e: entities)
|
||||||
|
delete e;
|
||||||
|
entities.clear();
|
||||||
|
|
||||||
|
std::istringstream is(buf_code);
|
||||||
|
std::string line;
|
||||||
|
while (std::getline(is, line)) {
|
||||||
|
if (line.size() == 0)
|
||||||
|
continue;
|
||||||
|
char *cmd = std::strtok(line.data(), " ");
|
||||||
|
#define CMD1(str) if (std::strcmp(cmd, str) == 0)
|
||||||
|
#define CMD(str) else if (std::strcmp(cmd, str) == 0)
|
||||||
|
if (!cmd)
|
||||||
|
continue;
|
||||||
|
EntityBase *e = NULL;
|
||||||
|
CMD1("HITBOX")
|
||||||
|
e = new Hitbox();
|
||||||
|
CMD("PLAYER")
|
||||||
|
e = new Player();
|
||||||
|
CMD("HAZARD_RESPAWN")
|
||||||
|
e = new HazardRespawn();
|
||||||
|
CMD("HAZARD")
|
||||||
|
e = new Hazard();
|
||||||
|
CMD("TEXTBOX")
|
||||||
|
e = new Textbox();
|
||||||
|
CMD("LEVEL_TRANSITION")
|
||||||
|
e = new LevelTransition();
|
||||||
|
CMD("CUTOFF")
|
||||||
|
cutoff = strtod(strtok(NULL, " "), NULL);
|
||||||
|
|
||||||
|
if (e != NULL) {
|
||||||
|
e->from_strtok();
|
||||||
|
entities.push_back(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
buf_code.clear();
|
||||||
|
}
|
||||||
|
ig::EndMenu();
|
||||||
|
}
|
||||||
|
|
||||||
|
Vec2 center = Vec2(ig::GetIO().DisplaySize) * 0.5 - offset;
|
||||||
|
ig::SeparatorText("Add Entity");
|
||||||
|
if (ig::Button("Hitbox"))
|
||||||
|
entities.push_back((new Hitbox())->setpos(center));
|
||||||
|
ig::SameLine();
|
||||||
|
if (ig::Button("Player"))
|
||||||
|
entities.push_back((new Player())->setpos(center));
|
||||||
|
ig::SameLine();
|
||||||
|
if (ig::Button("Hazard Respawn"))
|
||||||
|
entities.push_back((new HazardRespawn())->setpos(center));
|
||||||
|
if (ig::Button("Hazard"))
|
||||||
|
entities.push_back((new Hazard())->setpos(center));
|
||||||
|
ig::SameLine();
|
||||||
|
if (ig::Button("Textbox"))
|
||||||
|
entities.push_back((new Textbox())->setpos(center));
|
||||||
|
ig::SameLine();
|
||||||
|
if (ig::Button("Level Transition"))
|
||||||
|
entities.push_back((new LevelTransition())->setpos(center));
|
||||||
|
|
||||||
|
DragDouble("Cutoff depth", &cutoff);
|
||||||
|
|
||||||
|
ig::SeparatorText("Entities");
|
||||||
|
if (ig::Selectable("<<< CLEAR >>>", selected_entity == NULL))
|
||||||
|
selected_entity = NULL;
|
||||||
|
ig::Separator();
|
||||||
|
|
||||||
|
for (EntityBase *e: entities) {
|
||||||
|
ig::PushID(e);
|
||||||
|
if (ig::Selectable(e->type().c_str(), selected_entity == e))
|
||||||
|
selected_entity = e;
|
||||||
|
if (ig::IsItemHovered())
|
||||||
|
if (ig::IsMouseDoubleClicked(ImGuiMouseButton_Right))
|
||||||
|
to_delete = e;
|
||||||
|
ig::PopID();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ig::End();
|
||||||
|
|
||||||
|
if (ig::Begin("Properities") && selected_entity != NULL) {
|
||||||
|
ig::PushID(selected_entity);
|
||||||
|
selected_entity->imgui();
|
||||||
|
ig::PopID();
|
||||||
|
}
|
||||||
|
ig::End();
|
||||||
|
|
||||||
|
ImVec2 screen_size = ig::GetIO().DisplaySize;
|
||||||
|
ImDrawList *drawlist = ig::GetBackgroundDrawList();
|
||||||
|
drawlist->AddLine(ImVec2(0, offset.y), ImVec2(screen_size.x, offset.y), IM_COL32_WHITE);
|
||||||
|
drawlist->AddLine(ImVec2(offset.x, 0), ImVec2(offset.x, screen_size.y), IM_COL32_WHITE);
|
||||||
|
drawlist->AddLine(ImVec2(0, cutoff + offset.y), ImVec2(screen_size.x, cutoff + offset.y), IM_COL32(255, 0, 0, 255));
|
||||||
|
// Draw every entity
|
||||||
|
for (EntityBase *e: entities)
|
||||||
|
e->draw(offset, e == selected_entity);
|
||||||
|
|
||||||
|
|
||||||
|
static std::string buff;
|
||||||
|
buff.clear();
|
||||||
|
buff = "CUTOFF " + std::to_string((int)std::round(cutoff)) + "\n";
|
||||||
|
for (EntityBase *e: entities) {
|
||||||
|
buff += e->to_file();
|
||||||
|
}
|
||||||
|
if (ig::Begin("Output")) {
|
||||||
|
if (ig::Button("Copy!"))
|
||||||
|
ig::SetClipboardText(buff.c_str());
|
||||||
|
ig::InputTextMultiline("##Text", &buff, ImVec2(-1, -1), ImGuiInputTextFlags_ReadOnly);
|
||||||
|
}
|
||||||
|
ig::End();
|
||||||
|
|
||||||
|
|
||||||
|
if (to_delete != NULL) {
|
||||||
|
entities.remove(to_delete);
|
||||||
|
to_delete = NULL;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
177
map_types.hpp
177
map_types.hpp
@ -3,18 +3,24 @@
|
|||||||
#include "types.hpp"
|
#include "types.hpp"
|
||||||
#include "ig001.hpp"
|
#include "ig001.hpp"
|
||||||
#include "gui/imgui/imgui_stdlib.h"
|
#include "gui/imgui/imgui_stdlib.h"
|
||||||
|
#include <cstdlib>
|
||||||
|
#include <cstring>
|
||||||
|
#include <iterator>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
|
|
||||||
class EntityBase {
|
class EntityBase {
|
||||||
public:
|
public:
|
||||||
|
virtual ~EntityBase() {}
|
||||||
virtual std::string type() = 0;
|
virtual std::string type() = 0;
|
||||||
|
|
||||||
virtual std::string to_file() = 0;
|
virtual std::string to_file() = 0;
|
||||||
|
virtual void from_strtok() = 0;
|
||||||
|
|
||||||
// Pointer to the entity base is pushed outside
|
// Pointer to the entity base is pushed outside
|
||||||
virtual void imgui() {}
|
virtual void imgui() {}
|
||||||
virtual void draw(Vec2 offset, bool selected) {}
|
virtual void draw(Vec2 offset, bool selected) {}
|
||||||
|
virtual EntityBase *setpos(Vec2 pos) { return this; }
|
||||||
};
|
};
|
||||||
|
|
||||||
inline static void draw_box2(Box2 box, bool selected, ImU32 color) {
|
inline static void draw_box2(Box2 box, bool selected, ImU32 color) {
|
||||||
@ -34,6 +40,10 @@ inline static void draw_vec2(Vec2 vec, bool selected, ImU32 color) {
|
|||||||
list->AddCircle(vec.im(), 7.0f, color);
|
list->AddCircle(vec.im(), 7.0f, color);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define TOKEN (strtok(NULL, " "))
|
||||||
|
#define TOKEN_INT (atoi(TOKEN))
|
||||||
|
#define TOKEN_DOUBLE (strtod(TOKEN, NULL))
|
||||||
|
|
||||||
|
|
||||||
// Defined in bundle.cpp
|
// Defined in bundle.cpp
|
||||||
extern char buf[1024];
|
extern char buf[1024];
|
||||||
@ -42,12 +52,25 @@ class Hitbox: public EntityBase {
|
|||||||
public:
|
public:
|
||||||
std::string type() override { return "hitbox"; }
|
std::string type() override { return "hitbox"; }
|
||||||
std::string to_file() override {
|
std::string to_file() override {
|
||||||
snprintf(buf, sizeof(buf), "HITBOX %lf %lf %lf %lf\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y);
|
snprintf(buf, sizeof(buf), "HITBOX %.0lf %.0lf %.0lf %.0lf\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y);
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
|
||||||
void imgui() override { DragBox2("", &box); }
|
void from_strtok() override {
|
||||||
void draw(Vec2 offset, bool selected) override { draw_box2(box.offset(offset), selected, IM_COL32(0, 255, 0, 255)); }
|
double a, b, c, d;
|
||||||
|
a = TOKEN_DOUBLE;
|
||||||
|
b = TOKEN_DOUBLE;
|
||||||
|
c = TOKEN_DOUBLE;
|
||||||
|
d = TOKEN_DOUBLE;
|
||||||
|
box = Box2(a, b, c, d);
|
||||||
|
}
|
||||||
|
|
||||||
|
void imgui() override { DragBox2("", &box); }
|
||||||
|
void draw(Vec2 offset, bool selected) override { draw_box2(box.offset(offset), selected, IM_COL32(0, 255, 0, 255)); }
|
||||||
|
EntityBase *setpos(Vec2 pos) override {
|
||||||
|
box.lefttop = pos;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
Box2 box;
|
Box2 box;
|
||||||
};
|
};
|
||||||
@ -56,12 +79,22 @@ class Player: public EntityBase {
|
|||||||
public:
|
public:
|
||||||
std::string type() override { return "player"; }
|
std::string type() override { return "player"; }
|
||||||
std::string to_file() override {
|
std::string to_file() override {
|
||||||
snprintf(buf, sizeof(buf), "PLAYER %lf %lf\n", pos.x, pos.y);
|
snprintf(buf, sizeof(buf), "PLAYER %.0lf %.0lf\n", pos.x, pos.y);
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
void from_strtok() override {
|
||||||
|
double a, b, c, d;
|
||||||
|
a = TOKEN_DOUBLE;
|
||||||
|
b = TOKEN_DOUBLE;
|
||||||
|
pos = Vec2(a, b);
|
||||||
|
}
|
||||||
|
|
||||||
void imgui() override { DragVec2("Player Spawn", &pos); }
|
void imgui() override { DragVec2("Player Spawn", &pos); }
|
||||||
void draw(Vec2 offset, bool selected) override { draw_vec2(pos, selected, IM_COL32_WHITE); }
|
void draw(Vec2 offset, bool selected) override { draw_vec2(pos + offset, selected, IM_COL32_WHITE); }
|
||||||
|
EntityBase *setpos(Vec2 pos) override {
|
||||||
|
this->pos = pos;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
Vec2 pos;
|
Vec2 pos;
|
||||||
};
|
};
|
||||||
@ -70,17 +103,33 @@ class HazardRespawn: public EntityBase {
|
|||||||
public:
|
public:
|
||||||
std::string type() override { return "hazard_respawn"; }
|
std::string type() override { return "hazard_respawn"; }
|
||||||
std::string to_file() override {
|
std::string to_file() override {
|
||||||
snprintf(buf, sizeof(buf), "HAZARD_RESPAWN %lf %lf %lf %lf %lf %lf\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y, pos.x, pos.y);
|
snprintf(buf, sizeof(buf), "HAZARD_RESPAWN %.0lf %.0lf %.0lf %.0lf %.0lf %.0lf\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y, pos.x, pos.y);
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
void from_strtok() override {
|
||||||
|
double a, b, c, d, e, f;
|
||||||
|
a = TOKEN_DOUBLE;
|
||||||
|
b = TOKEN_DOUBLE;
|
||||||
|
c = TOKEN_DOUBLE;
|
||||||
|
d = TOKEN_DOUBLE;
|
||||||
|
e = TOKEN_DOUBLE;
|
||||||
|
f = TOKEN_DOUBLE;
|
||||||
|
box = Box2(a, b, c, d);
|
||||||
|
pos = Vec2(e, f);
|
||||||
|
}
|
||||||
|
|
||||||
void imgui() override {
|
void imgui() override {
|
||||||
DragBox2("", &box);
|
DragBox2("", &box);
|
||||||
DragVec2("Respawn", &pos);
|
DragVec2("Respawn", &pos);
|
||||||
}
|
}
|
||||||
void draw(Vec2 offset, bool selected) override {
|
void draw(Vec2 offset, bool selected) override {
|
||||||
draw_box2(box, selected, IM_COL32(255, 0, 255, 255));
|
draw_box2(box.offset(offset), selected, IM_COL32(255, 0, 255, 255));
|
||||||
draw_vec2(pos, selected, IM_COL32(255, 0, 255, 255));
|
draw_vec2(pos + offset, selected, IM_COL32(255, 0, 255, 255));
|
||||||
|
}
|
||||||
|
EntityBase *setpos(Vec2 pos) override {
|
||||||
|
box.lefttop = pos;
|
||||||
|
this->pos = pos;
|
||||||
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
Box2 box;
|
Box2 box;
|
||||||
@ -91,12 +140,24 @@ class Hazard: public EntityBase {
|
|||||||
public:
|
public:
|
||||||
std::string type() override { return "hazard"; }
|
std::string type() override { return "hazard"; }
|
||||||
std::string to_file() override {
|
std::string to_file() override {
|
||||||
snprintf(buf, sizeof(buf), "HAZARD %lf %lf %lf %lf\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y);
|
snprintf(buf, sizeof(buf), "HAZARD %.0lf %.0lf %.0lf %.0lf\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y);
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
void from_strtok() override {
|
||||||
|
double a, b, c, d;
|
||||||
|
a = TOKEN_DOUBLE;
|
||||||
|
b = TOKEN_DOUBLE;
|
||||||
|
c = TOKEN_DOUBLE;
|
||||||
|
d = TOKEN_DOUBLE;
|
||||||
|
box = Box2(a, b, c, d);
|
||||||
|
}
|
||||||
|
|
||||||
void imgui() override { DragBox2("", &box); }
|
void imgui() override { DragBox2("", &box); }
|
||||||
void draw(Vec2 offset, bool selected) override { draw_box2(box, selected, IM_COL32(255, 0, 0, 255)); }
|
void draw(Vec2 offset, bool selected) override { draw_box2(box.offset(offset), selected, IM_COL32(255, 0, 0, 255)); }
|
||||||
|
EntityBase *setpos(Vec2 pos) override {
|
||||||
|
box.lefttop = pos;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
Box2 box;
|
Box2 box;
|
||||||
};
|
};
|
||||||
@ -106,7 +167,7 @@ public:
|
|||||||
std::string type() override { return "textbox"; }
|
std::string type() override { return "textbox"; }
|
||||||
std::string to_file() override {
|
std::string to_file() override {
|
||||||
std::string str;
|
std::string str;
|
||||||
snprintf(buf, sizeof(buf), "TEXTBOX %lf %lf %lf %lf ", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y);
|
snprintf(buf, sizeof(buf), "TEXTBOX %.0lf %.0lf %.0lf %.0lf %s ", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y, render_bundle.c_str());
|
||||||
str += buf;
|
str += buf;
|
||||||
|
|
||||||
// Escape all the whitespaces
|
// Escape all the whitespaces
|
||||||
@ -129,18 +190,98 @@ public:
|
|||||||
str += "\n";
|
str += "\n";
|
||||||
return str;
|
return str;
|
||||||
}
|
}
|
||||||
|
void from_strtok() override {
|
||||||
|
double a, b, c, d;
|
||||||
|
a = TOKEN_DOUBLE;
|
||||||
|
b = TOKEN_DOUBLE;
|
||||||
|
c = TOKEN_DOUBLE;
|
||||||
|
d = TOKEN_DOUBLE;
|
||||||
|
box = Box2(a, b, c, d);
|
||||||
|
|
||||||
|
char *t = TOKEN;
|
||||||
|
render_bundle = (t ? t : "");
|
||||||
|
t = TOKEN;
|
||||||
|
std::string temp = (t ? t : "");
|
||||||
|
text.clear();
|
||||||
|
for (int i = 0; i < temp.size(); i++) {
|
||||||
|
if (temp[i] == '\\') {
|
||||||
|
if (i == temp.size() - 1)
|
||||||
|
text.push_back('\\'); // Weird case
|
||||||
|
else {
|
||||||
|
if (temp[i + 1] == 's')
|
||||||
|
text.push_back(' ');
|
||||||
|
else if (temp[i + 1] == 'n')
|
||||||
|
text.push_back('\n');
|
||||||
|
else if (temp[i + 1] == 't')
|
||||||
|
text.push_back('\t');
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
} else
|
||||||
|
text.push_back(temp[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void imgui() override {
|
void imgui() override {
|
||||||
DragBox2("", &box);
|
DragBox2("", &box);
|
||||||
|
ig::InputText("Render Bundle", &render_bundle);
|
||||||
ig::InputTextMultiline("##Text", &text, ImVec2(-1, 0));
|
ig::InputTextMultiline("##Text", &text, ImVec2(-1, 0));
|
||||||
}
|
}
|
||||||
void draw(Vec2 offset, bool selected) override {
|
void draw(Vec2 offset, bool selected) override {
|
||||||
draw_box2(box, selected, IM_COL32(0, 0, 255, 255));
|
draw_box2(box.offset(offset), selected, IM_COL32(0, 0, 255, 255));
|
||||||
// Draw text
|
// Draw text
|
||||||
ImDrawList *list = ig::GetBackgroundDrawList();
|
ImDrawList *list = ig::GetBackgroundDrawList();
|
||||||
list->AddText(box.lefttop.im(), IM_COL32_WHITE, text.c_str());
|
list->AddText((box.lefttop + offset).im(), IM_COL32_WHITE, text.c_str());
|
||||||
|
list->AddText((box.lefttop + offset + Vec2(0, box.size.y)).im(), IM_COL32_WHITE, render_bundle.c_str());
|
||||||
|
}
|
||||||
|
EntityBase *setpos(Vec2 pos) override {
|
||||||
|
box.lefttop = pos;
|
||||||
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string text;
|
std::string text;
|
||||||
|
std::string render_bundle;
|
||||||
Box2 box;
|
Box2 box;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class LevelTransition: public EntityBase {
|
||||||
|
public:
|
||||||
|
std::string type() override { return "level_transition"; }
|
||||||
|
std::string to_file() override {
|
||||||
|
snprintf(buf, sizeof(buf), "LEVEL_TRANSITION %.0lf %.0lf %.0lf %.0lf %s\n", box.lefttop.x, box.lefttop.y, box.size.x, box.size.y, next_level.c_str());
|
||||||
|
return buf;
|
||||||
|
}
|
||||||
|
|
||||||
|
void from_strtok() override {
|
||||||
|
double a, b, c, d;
|
||||||
|
a = TOKEN_DOUBLE;
|
||||||
|
b = TOKEN_DOUBLE;
|
||||||
|
c = TOKEN_DOUBLE;
|
||||||
|
d = TOKEN_DOUBLE;
|
||||||
|
box = Box2(a, b, c, d);
|
||||||
|
|
||||||
|
char *t = TOKEN;
|
||||||
|
if (t != NULL)
|
||||||
|
next_level = t;
|
||||||
|
else
|
||||||
|
next_level.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
void imgui() override {
|
||||||
|
DragBox2("", &box);
|
||||||
|
ig::InputText("Next Level", &next_level);
|
||||||
|
}
|
||||||
|
void draw(Vec2 offset, bool selected) override {
|
||||||
|
draw_box2(box.offset(offset), selected, IM_COL32(255, 255, 0, 255));
|
||||||
|
// Draw text
|
||||||
|
ImDrawList *list = ig::GetBackgroundDrawList();
|
||||||
|
list->AddText((box.lefttop + offset).im(), IM_COL32_WHITE, next_level.c_str());
|
||||||
|
}
|
||||||
|
EntityBase *setpos(Vec2 pos) override {
|
||||||
|
box.lefttop = pos;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
Box2 box;
|
||||||
|
std::string next_level;
|
||||||
|
};
|
||||||
|
@ -43,6 +43,9 @@ public:
|
|||||||
Vec2 operator+(Vec2 other) const {
|
Vec2 operator+(Vec2 other) const {
|
||||||
return Vec2(x + other.x, y + other.y);
|
return Vec2(x + other.x, y + other.y);
|
||||||
}
|
}
|
||||||
|
Vec2 operator-(Vec2 other) const {
|
||||||
|
return Vec2(x - other.x, y - other.y);
|
||||||
|
}
|
||||||
Vec2 operator*(double other) const {
|
Vec2 operator*(double other) const {
|
||||||
return Vec2(x * other, y * other);
|
return Vec2(x * other, y * other);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user