diff --git a/samples/simple/styled.xml b/samples/simple/styled.xml
index 62a6be7..2dc03f6 100644
--- a/samples/simple/styled.xml
+++ b/samples/simple/styled.xml
@@ -136,7 +136,7 @@
margin-bottom: 2px;
}
- input[type="text"], input[type="password"] {
+ input[type="text"], input[type="password"], input[type="number"] {
display: block;
padding: 0.2em 0.5em;
margin: 2px 2px 10px 2px;
@@ -145,7 +145,7 @@
background-color: #222222;
}
- input[type="text"]:active, input[type="password"]:active {
+ input[type="text"]:active, input[type="password"]:active, input[type="number"]:active {
margin-top: 0px;
margin-left: 0px;
margin-right: 0px;
@@ -244,6 +244,10 @@
+
+
+
+
diff --git a/src/extras/xhtml.h b/src/extras/xhtml.h
index 57ea0f8..202bdd4 100644
--- a/src/extras/xhtml.h
+++ b/src/extras/xhtml.h
@@ -210,6 +210,7 @@ namespace ImVue {
, max(100.0f)
, step(1.0f)
, name(0)
+ , speed(1.0f)
, mValue(0)
, mModel(0)
, mValueUpdated(false)
@@ -377,6 +378,10 @@ namespace ImVue {
break;
case RANGE:
changed = ImGui::SliderFloat(placeholder ? placeholder : "##slider", &mSliderValue, min, max, format ? format : "%.3f", step);
+ break;
+ case NUMBER:
+ changed = ImGui::DragFloat(placeholder ? placeholder : "##dragfloat", &mSliderValue, speed, min, max, format ? format : "%.3f", step);
+ break;
default:
// nothing
break;
@@ -427,6 +432,8 @@ namespace ImVue {
mType = RADIO;
} else if(ImStricmp(type, "range") == 0) {
mType = RANGE;
+ } else if(ImStricmp(type, "number") == 0) {
+ mType = NUMBER;
}
if(mType == TEXT || mType == PASSWORD) {
@@ -487,6 +494,8 @@ namespace ImVue {
// radio only
char* name;
+ // number only
+ float speed;
private:
void syncModel(bool write = false)
@@ -515,6 +524,7 @@ namespace ImVue {
case RADIO:
(*mScriptState)[mModel] = mValue ? mValue : placeholder;
break;
+ case NUMBER:
case RANGE:
(*mScriptState)[mModel] = mSliderValue;
default:
@@ -553,6 +563,7 @@ namespace ImVue {
resetState(CHECKED);
break;
+ case NUMBER:
case RANGE:
mSliderValue = object.as();
default:
@@ -619,6 +630,7 @@ namespace ImVue {
.attribute("max", &Input::max)
.attribute("step", &Input::step)
.attribute("format", &Input::format)
+ .attribute("speed", &Input::speed)
.attribute("placeholder", &Input::placeholder);
}
diff --git a/src/imvue.cpp b/src/imvue.cpp
index 76edfa7..702fd7c 100644
--- a/src/imvue.cpp
+++ b/src/imvue.cpp
@@ -197,7 +197,7 @@ namespace ImVue {
res = builder->create(node, ctx, sctx, parent);
} else {
// then try to create a component
- res = createComponent(node, ctx, sctx);
+ res = createComponent(node, ctx, sctx, parent);
}
if(res && sctx) {
@@ -206,7 +206,7 @@ namespace ImVue {
return res;
}
- Element* ComponentContainer::createComponent(rapidxml::xml_node<>* node, Context* ctx, ScriptState::Context* sctx)
+ Element* ComponentContainer::createComponent(rapidxml::xml_node<>* node, Context* ctx, ScriptState::Context* sctx, Element* parent)
{
ImU32 nodeID = ImHashStr(node->name());
if(mComponents.count(nodeID) == 0) {
@@ -215,7 +215,7 @@ namespace ImVue {
Component* component = mComponents[nodeID].create();
try {
- component->configure(node, ctx, sctx, this);
+ component->configure(node, ctx, sctx, parent);
} catch(...) {
delete component;
throw;
@@ -343,7 +343,7 @@ namespace ImVue {
, mData(data)
{
parseXML(tmpl.get());
- mFlags = mFlags | Element::COMPONENT;
+ mFlags = mFlags | Element::COMPONENT | Element::PSEUDO_ELEMENT;
}
Component::~Component()
diff --git a/src/imvue.h b/src/imvue.h
index d176426..1399631 100644
--- a/src/imvue.h
+++ b/src/imvue.h
@@ -150,7 +150,7 @@ namespace ImVue {
/**
* Creates component
*/
- Element* createComponent(rapidxml::xml_node<>* node, Context* ctx, ScriptState::Context* sctx);
+ Element* createComponent(rapidxml::xml_node<>* node, Context* ctx, ScriptState::Context* sctx, Element* parent);
void parseXML(const char* data);
diff --git a/src/imvue_context.cpp b/src/imvue_context.cpp
index ecaf8b8..46388bd 100644
--- a/src/imvue_context.cpp
+++ b/src/imvue_context.cpp
@@ -195,6 +195,7 @@ namespace ImVue {
Style* style = new Style(ctx->style);
Context* child = createContext(ctx->factory, script, ctx->texture, ctx->fs, ctx->fontManager, style, ctx->userdata);
child->parent = ctx;
+ child->scale = ctx->scale;
return child;
}
}
diff --git a/src/imvue_style.cpp b/src/imvue_style.cpp
index a29aee3..af47aba 100644
--- a/src/imvue_style.cpp
+++ b/src/imvue_style.cpp
@@ -530,6 +530,7 @@ namespace ImVue {
} else {
pos = window->Pos;
}
+ pos -= window->Scroll;
break;
}
case CSS_POSITION_FIXED:
@@ -1054,7 +1055,7 @@ namespace ImVue {
ImGuiWindow* window = GetCurrentWindowNoDefault();
if(window){
Element* parent = e->getParent();
- while(parent && parent->display == CSS_DISPLAY_INLINE) {
+ while(parent && (parent->display == CSS_DISPLAY_INLINE || (parent->getFlags() & Element::PSEUDO_ELEMENT) != 0)) {
parent = parent->getParent();
}
@@ -1348,8 +1349,6 @@ namespace ImVue {
if (code != CSS_OK)
IMVUE_EXCEPTION(StyleError, "failed to append base stylesheet: %s", css_error_to_string(code));
- if(mParent)
- mParent->appendSheets(ctx, false);
appendSheets(ctx, true);
return ctx;
}
@@ -1369,6 +1368,10 @@ namespace ImVue {
void Style::appendSheets(css_select_ctx* ctx, bool scoped)
{
+ if(mParent) {
+ mParent->appendSheets(ctx, false);
+ }
+
for(int i = 0; i < mSheets.size(); ++i) {
if(mSheets[i].scoped && !scoped) {
continue;
diff --git a/tests/resources/dimensions.imv b/tests/resources/dimensions.imv
new file mode 100644
index 0000000..ae1bdbe
--- /dev/null
+++ b/tests/resources/dimensions.imv
@@ -0,0 +1,7 @@
+
+
+
+
+
diff --git a/tests/resources/dimensions.xml b/tests/resources/dimensions.xml
new file mode 100644
index 0000000..4ec6156
--- /dev/null
+++ b/tests/resources/dimensions.xml
@@ -0,0 +1,25 @@
+
+
+
+
+
+
+
+
+
diff --git a/tests/unit/style.cpp b/tests/unit/style.cpp
index 594569f..b3934b7 100644
--- a/tests/unit/style.cpp
+++ b/tests/unit/style.cpp
@@ -4,6 +4,7 @@
#include "imvue_generated.h"
#include "imvue_errors.h"
#include "utils.h"
+#include "extras/xhtml.h"
#if defined(WITH_LUA)
#include "lua/script.h"
@@ -760,3 +761,83 @@ INSTANTIATE_TEST_CASE_P(
#endif
));
+#if defined(WITH_LUA)
+
+class TestStylesComponents : public ::testing::Test {
+
+ public:
+
+ TestStylesComponents()
+ : mDoc(0)
+ {
+ }
+
+ ~TestStylesComponents()
+ {
+ if(mDoc) {
+ delete mDoc;
+ mDoc = 0;
+ }
+ }
+
+ void SetUp() override
+ {
+ L = luaL_newstate();
+ luaL_openlibs(L);
+ ImVue::registerBindings(L);
+ }
+
+ void TearDown() override
+ {
+ if(mDoc) {
+ delete mDoc;
+ mDoc = 0;
+ }
+ lua_close(L);
+ }
+
+ ImVue::Document& createDoc(const char* path)
+ {
+ if(mDoc) {
+ delete mDoc;
+ }
+
+ ImVue::ElementFactory* factory = ImVue::createElementFactory();
+ factory->element("test");
+
+ ImVue::Context* ctx = ImVue::createContext(factory, new ImVue::LuaScriptState(L));
+ ImVue::Document doc(ctx);
+ char* data = ctx->fs->load(path);
+ try {
+ mDoc = new ImVue::Document(ctx);
+ mDoc->parse(data);
+ } catch(...) {
+ delete mDoc;
+ ImGui::MemFree(data);
+ throw;
+ }
+ ImGui::MemFree(data);
+
+ return *mDoc;
+ }
+
+ private:
+ ImVue::Document* mDoc;
+ lua_State* L;
+};
+
+TEST_F(TestStylesComponents, Dimensions)
+{
+ ImVue::Document& d = createDoc("dimensions.xml");
+ ImVector els = d.getChildren("#check", true);
+
+ ASSERT_GT(els.size(), 0);
+
+ renderDocument(d);
+
+ ImVue::HtmlContainer* div = els[0];
+ EXPECT_EQ(div->computedSize.x, 300);
+ EXPECT_EQ(div->computedSize.y, 300);
+}
+
+#endif