typed lua properties - closes #567

This commit is contained in:
Mikulas Florek 2015-10-19 00:14:16 +02:00
parent 8e674977df
commit 54d11b5d38
8 changed files with 148 additions and 23 deletions

View file

@ -35,11 +35,11 @@ void LuaScript::unload()
const char* LuaScript::getPropertyName(uint32_t hash) const
{
for (const char* name : m_properties)
for (auto& property : m_properties)
{
if (crc32(name) == hash)
if (crc32(property.name) == hash)
{
return name;
return property.name;
}
}
return nullptr;
@ -52,7 +52,7 @@ static bool isWhitespace(char c)
}
static void getToken(const char* src, char* dest, int size)
static const char* getToken(const char* src, char* dest, int size)
{
const char* in = src;
char* out = dest;
@ -70,6 +70,7 @@ static void getToken(const char* src, char* dest, int size)
--size;
}
*out = '\0';
return in;
}
@ -81,10 +82,24 @@ void LuaScript::parseProperties()
const char* prop = strstr(str, PROPERTY_MARK);
while (prop)
{
const char* prop_name = prop + PROPERTY_MARK_LENGTH + 1;
const char* token = prop + PROPERTY_MARK_LENGTH + 1;
PropertyName& token = m_properties.pushEmpty();
getToken(prop_name, token, sizeof(token));
Property& property = m_properties.pushEmpty();
token = getToken(token, property.name, sizeof(property.name));
char type[50];
token = getToken(token, type, sizeof(type));
if (strcmp(type, "entity") == 0)
{
property.type = Property::ENTITY;
}
else if (strcmp(type, "float") == 0)
{
property.type = Property::FLOAT;
}
else
{
property.type = Property::ANY;
}
prop = strstr(prop + 1, PROPERTY_MARK);
}

View file

@ -14,7 +14,17 @@ namespace Lumix
class LuaScript : public Resource
{
public:
typedef char PropertyName[50];
struct Property
{
char name[50];
enum Type
{
ENTITY,
FLOAT,
ANY
};
Type type;
};
public:
LuaScript(const Path& path,
@ -26,7 +36,7 @@ public:
virtual bool load(FS::IFile& file) override;
const char* getSourceCode() const { return m_source_code.c_str(); }
const char* getPropertyName(uint32_t hash) const;
const Array<PropertyName>& getPropertiesNames() const
const Array<Property>& getProperties() const
{
return m_properties;
}
@ -36,7 +46,7 @@ private:
private:
string m_source_code;
Array<PropertyName> m_properties;
Array<Property> m_properties;
};

View file

@ -153,6 +153,12 @@ public:
}
virtual LuaScript* getScriptResource(ComponentIndex cmp) const override
{
return getScript(cmp).m_script;
}
virtual const char* getPropertyValue(Lumix::ComponentIndex cmp, int index) const override
{
auto& script = getScript(cmp);
@ -188,7 +194,7 @@ public:
{
auto& script = getScript(cmp);
return script.m_script ? script.m_script->getPropertiesNames()[index] : "";
return script.m_script ? script.m_script->getProperties()[index].name : "";
}
@ -196,7 +202,7 @@ public:
{
auto& script = getScript(cmp);
return script.m_script ? script.m_script->getPropertiesNames().size() : 0;
return script.m_script ? script.m_script->getProperties().size() : 0;
}

View file

@ -9,25 +9,29 @@ namespace Lumix
{
class LuaScript;
class LuaScriptScene : public IScene
{
public:
struct Property
{
Property(Lumix::IAllocator& allocator)
Property(IAllocator& allocator)
: m_value(allocator)
{
}
Lumix::string m_value;
string m_value;
uint32_t m_name_hash;
};
public:
virtual int getPropertyCount(Lumix::ComponentIndex cmp) const = 0;
virtual const char* getPropertyName(Lumix::ComponentIndex cmp, int index) const = 0;
virtual const char* getPropertyValue(Lumix::ComponentIndex cmp, int index) const = 0;
virtual void setPropertyValue(Lumix::ComponentIndex cmp,
virtual int getPropertyCount(ComponentIndex cmp) const = 0;
virtual const char* getPropertyName(ComponentIndex cmp, int index) const = 0;
virtual const char* getPropertyValue(ComponentIndex cmp, int index) const = 0;
virtual LuaScript* getScriptResource(ComponentIndex cmp) const = 0;
virtual void setPropertyValue(ComponentIndex cmp,
const char* name,
const char* value) = 0;
};

View file

@ -94,7 +94,7 @@ class Terrain
void setGrassTypePath(int index, const Path& path);
void setGrassTypeGround(int index, int ground);
void setGrassTypeDensity(int index, int density);
void setGrassDistance(int value) { m_grass_distance = value; }
void setGrassDistance(int value) { m_grass_distance = value; forceGrassUpdate(); }
void setMaterial(Material* material);
void getInfos(Array<const TerrainInfo*>& infos, const Vec3& camera_pos, LIFOAllocator& allocator);

View file

@ -156,6 +156,8 @@ public:
if (ImGui::BeginChild("right", half_size, true))
{
ImGui::Text("Version 0.17. - News");
ImGui::BulletText("Lua properties with types");
ImGui::BulletText("Moving the Light Texel-Sized Increments");
ImGui::BulletText("Terrain brush for removing entities");
ImGui::BulletText("Improved shadows on terrain");
ImGui::BulletText("Fog height");
@ -598,8 +600,6 @@ public:
}
ImGui::Separator();
auto entity = universe->getFirstEntity();
struct ListBoxData
{
Lumix::WorldEditor* m_editor;

View file

@ -4,6 +4,7 @@
#include "editor/world_editor.h"
#include "engine/engine.h"
#include "engine/property_descriptor.h"
#include "lua_script/lua_script_manager.h"
#include "lua_script/lua_script_system.h"
#include "ocornut-imgui/imgui.h"
#include "terrain_editor.h"
@ -245,6 +246,66 @@ void PropertyGrid::showComponentProperties(Lumix::ComponentUID cmp)
}
bool PropertyGrid::entityInput(const char* label, const char* str_id, Lumix::Entity& entity) const
{
const auto& style = ImGui::GetStyle();
float item_w = ImGui::CalcItemWidth();
ImGui::PushItemWidth(
item_w - ImGui::CalcTextSize("...").x - style.FramePadding.x * 2 - style.ItemSpacing.x);
char buf[50];
getEntityListDisplayName(m_editor, buf, sizeof(buf), entity);
ImGui::LabelText("", buf);
ImGui::SameLine();
StringBuilder<30> popup_name("pu", str_id);
if (ImGui::Button(StringBuilder<30>("...###br", str_id)))
{
ImGui::OpenPopup(popup_name);
}
ImGui::SameLine();
ImGui::Text(label);
ImGui::PopItemWidth();
if (ImGui::BeginPopup(popup_name))
{
struct ListBoxData
{
Lumix::WorldEditor* m_editor;
Lumix::Universe* universe;
char buffer[1024];
static bool itemsGetter(void* data, int idx, const char** txt)
{
auto* d = static_cast<ListBoxData*>(data);
auto entity = d->universe->getEntityFromDenseIdx(idx);
getEntityListDisplayName(*d->m_editor, d->buffer, sizeof(d->buffer), entity);
*txt = d->buffer;
return true;
}
};
ListBoxData data;
Lumix::Universe* universe = m_editor.getUniverse();
data.universe = universe;
data.m_editor = &m_editor;
static int current_item;
if (ImGui::ListBox("Entities",
&current_item,
&ListBoxData::itemsGetter,
&data,
universe->getEntityCount(),
15))
{
entity = universe->getEntityFromDenseIdx(current_item);
ImGui::CloseCurrentPopup();
ImGui::EndPopup();
return true;
};
ImGui::EndPopup();
}
return false;
}
void PropertyGrid::onLuaScriptGui(Lumix::ComponentUID cmp)
{
auto* scene = static_cast<Lumix::LuaScriptScene*>(cmp.scene);
@ -254,9 +315,37 @@ void PropertyGrid::onLuaScriptGui(Lumix::ComponentUID cmp)
char buf[256];
Lumix::copyString(buf, scene->getPropertyValue(cmp.index, i));
const char* property_name = scene->getPropertyName(cmp.index, i);
if (ImGui::InputText(property_name, buf, sizeof(buf)))
auto* script_res = scene->getScriptResource(cmp.index);
switch (script_res->getProperties()[i].type)
{
scene->setPropertyValue(cmp.index, property_name, buf);
case Lumix::LuaScript::Property::FLOAT:
{
float f = (float)atof(buf);
if (ImGui::DragFloat(property_name, &f))
{
Lumix::toCString(f, buf, sizeof(buf), 5);
scene->setPropertyValue(cmp.index, property_name, buf);
}
}
break;
case Lumix::LuaScript::Property::ENTITY:
{
Lumix::Entity e;
Lumix::fromCString(buf, sizeof(buf), &e);
if (entityInput(property_name, StringBuilder<20>("", cmp.index), e))
{
Lumix::toCString(e, buf, sizeof(buf));
scene->setPropertyValue(cmp.index, property_name, buf);
}
}
break;
case Lumix::LuaScript::Property::ANY:
if (ImGui::InputText(property_name, buf, sizeof(buf)))
{
scene->setPropertyValue(cmp.index, property_name, buf);
}
break;
}
}
}

View file

@ -37,6 +37,7 @@ class PropertyGrid
void showComponentProperties(Lumix::ComponentUID cmp);
void showCoreProperties(Lumix::Entity entity);
const char* getComponentTypeName(Lumix::ComponentUID cmp) const;
bool entityInput(const char* label, const char* str_id, Lumix::Entity& entity) const;
private:
Lumix::WorldEditor& m_editor;