Unlink XCNewEditor default shell from ImGui compat slice
This commit is contained in:
@@ -5,7 +5,9 @@
|
||||
set(UI_TEST_SOURCES
|
||||
test_ui_core.cpp
|
||||
test_ui_editor_collection_primitives.cpp
|
||||
test_ui_editor_panel_chrome.cpp
|
||||
test_ui_expansion_model.cpp
|
||||
test_ui_flat_hierarchy_helpers.cpp
|
||||
test_ui_keyboard_navigation_model.cpp
|
||||
test_ui_property_edit_model.cpp
|
||||
test_layout_engine.cpp
|
||||
|
||||
126
tests/Core/UI/test_ui_editor_panel_chrome.cpp
Normal file
126
tests/Core/UI/test_ui_editor_panel_chrome.cpp
Normal file
@@ -0,0 +1,126 @@
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <XCEngine/UI/DrawData.h>
|
||||
#include <XCEngine/UI/Widgets/UIEditorPanelChrome.h>
|
||||
|
||||
namespace {
|
||||
|
||||
using XCEngine::UI::UIColor;
|
||||
using XCEngine::UI::UIDrawCommandType;
|
||||
using XCEngine::UI::UIDrawList;
|
||||
using XCEngine::UI::UIRect;
|
||||
using XCEngine::UI::Widgets::AppendUIEditorPanelChromeBackground;
|
||||
using XCEngine::UI::Widgets::AppendUIEditorPanelChromeForeground;
|
||||
using XCEngine::UI::Widgets::BuildUIEditorPanelChromeHeaderRect;
|
||||
using XCEngine::UI::Widgets::ResolveUIEditorPanelChromeBorderColor;
|
||||
using XCEngine::UI::Widgets::ResolveUIEditorPanelChromeBorderThickness;
|
||||
using XCEngine::UI::Widgets::UIEditorPanelChromePalette;
|
||||
using XCEngine::UI::Widgets::UIEditorPanelChromeState;
|
||||
using XCEngine::UI::Widgets::UIEditorPanelChromeText;
|
||||
|
||||
void ExpectColorEq(
|
||||
const UIColor& actual,
|
||||
const UIColor& expected) {
|
||||
EXPECT_FLOAT_EQ(actual.r, expected.r);
|
||||
EXPECT_FLOAT_EQ(actual.g, expected.g);
|
||||
EXPECT_FLOAT_EQ(actual.b, expected.b);
|
||||
EXPECT_FLOAT_EQ(actual.a, expected.a);
|
||||
}
|
||||
|
||||
TEST(UIEditorPanelChromeTest, HeaderRectAndBorderPolicyMatchNativeShellCardChrome) {
|
||||
const UIRect panelRect(100.0f, 200.0f, 320.0f, 180.0f);
|
||||
const UIEditorPanelChromePalette palette = {};
|
||||
|
||||
const auto headerRect = BuildUIEditorPanelChromeHeaderRect(panelRect);
|
||||
EXPECT_FLOAT_EQ(headerRect.x, 100.0f);
|
||||
EXPECT_FLOAT_EQ(headerRect.y, 200.0f);
|
||||
EXPECT_FLOAT_EQ(headerRect.width, 320.0f);
|
||||
EXPECT_FLOAT_EQ(headerRect.height, 42.0f);
|
||||
|
||||
ExpectColorEq(
|
||||
ResolveUIEditorPanelChromeBorderColor(UIEditorPanelChromeState(), palette),
|
||||
palette.borderColor);
|
||||
ExpectColorEq(
|
||||
ResolveUIEditorPanelChromeBorderColor(UIEditorPanelChromeState{ false, true }, palette),
|
||||
palette.hoveredAccentColor);
|
||||
ExpectColorEq(
|
||||
ResolveUIEditorPanelChromeBorderColor(UIEditorPanelChromeState{ true, true }, palette),
|
||||
palette.accentColor);
|
||||
|
||||
EXPECT_FLOAT_EQ(ResolveUIEditorPanelChromeBorderThickness(UIEditorPanelChromeState()), 1.0f);
|
||||
EXPECT_FLOAT_EQ(ResolveUIEditorPanelChromeBorderThickness(UIEditorPanelChromeState{ true, false }), 2.0f);
|
||||
}
|
||||
|
||||
TEST(UIEditorPanelChromeTest, BackgroundAppendEmitsSurfaceOutlineAndHeaderFill) {
|
||||
UIDrawList drawList("PanelChrome");
|
||||
const UIRect panelRect(40.0f, 60.0f, 400.0f, 280.0f);
|
||||
const UIEditorPanelChromeState state{ true, false };
|
||||
const UIEditorPanelChromePalette palette = {};
|
||||
|
||||
AppendUIEditorPanelChromeBackground(drawList, panelRect, state, palette);
|
||||
|
||||
ASSERT_EQ(drawList.GetCommandCount(), 3u);
|
||||
const auto& commands = drawList.GetCommands();
|
||||
EXPECT_EQ(commands[0].type, UIDrawCommandType::FilledRect);
|
||||
EXPECT_EQ(commands[1].type, UIDrawCommandType::RectOutline);
|
||||
EXPECT_EQ(commands[2].type, UIDrawCommandType::FilledRect);
|
||||
|
||||
EXPECT_FLOAT_EQ(commands[0].rect.x, 40.0f);
|
||||
EXPECT_FLOAT_EQ(commands[0].rounding, 18.0f);
|
||||
ExpectColorEq(commands[0].color, palette.surfaceColor);
|
||||
|
||||
EXPECT_FLOAT_EQ(commands[1].thickness, 2.0f);
|
||||
EXPECT_FLOAT_EQ(commands[1].rounding, 18.0f);
|
||||
ExpectColorEq(commands[1].color, palette.accentColor);
|
||||
|
||||
EXPECT_FLOAT_EQ(commands[2].rect.height, 42.0f);
|
||||
EXPECT_FLOAT_EQ(commands[2].rounding, 18.0f);
|
||||
ExpectColorEq(commands[2].color, palette.headerColor);
|
||||
}
|
||||
|
||||
TEST(UIEditorPanelChromeTest, ForegroundAppendPlacesTitleSubtitleAndFooterAtCurrentOffsets) {
|
||||
UIDrawList drawList("PanelChromeText");
|
||||
const UIRect panelRect(100.0f, 200.0f, 320.0f, 180.0f);
|
||||
const UIEditorPanelChromePalette palette = {};
|
||||
const UIEditorPanelChromeText text{
|
||||
"XCUI Demo",
|
||||
"native queued offscreen surface",
|
||||
"Active | 42 elements | 9 cmds"
|
||||
};
|
||||
|
||||
AppendUIEditorPanelChromeForeground(drawList, panelRect, text, palette);
|
||||
|
||||
ASSERT_EQ(drawList.GetCommandCount(), 3u);
|
||||
const auto& commands = drawList.GetCommands();
|
||||
EXPECT_EQ(commands[0].type, UIDrawCommandType::Text);
|
||||
EXPECT_EQ(commands[1].type, UIDrawCommandType::Text);
|
||||
EXPECT_EQ(commands[2].type, UIDrawCommandType::Text);
|
||||
|
||||
EXPECT_EQ(commands[0].text, "XCUI Demo");
|
||||
EXPECT_FLOAT_EQ(commands[0].position.x, 116.0f);
|
||||
EXPECT_FLOAT_EQ(commands[0].position.y, 212.0f);
|
||||
ExpectColorEq(commands[0].color, palette.textPrimary);
|
||||
|
||||
EXPECT_EQ(commands[1].text, "native queued offscreen surface");
|
||||
EXPECT_FLOAT_EQ(commands[1].position.x, 116.0f);
|
||||
EXPECT_FLOAT_EQ(commands[1].position.y, 228.0f);
|
||||
ExpectColorEq(commands[1].color, palette.textSecondary);
|
||||
|
||||
EXPECT_EQ(commands[2].text, "Active | 42 elements | 9 cmds");
|
||||
EXPECT_FLOAT_EQ(commands[2].position.x, 116.0f);
|
||||
EXPECT_FLOAT_EQ(commands[2].position.y, 362.0f);
|
||||
ExpectColorEq(commands[2].color, palette.textMuted);
|
||||
}
|
||||
|
||||
TEST(UIEditorPanelChromeTest, ForegroundAppendSkipsEmptyStrings) {
|
||||
UIDrawList drawList("PanelChromeEmptyText");
|
||||
|
||||
AppendUIEditorPanelChromeForeground(
|
||||
drawList,
|
||||
UIRect(0.0f, 0.0f, 320.0f, 180.0f),
|
||||
UIEditorPanelChromeText{});
|
||||
|
||||
EXPECT_EQ(drawList.GetCommandCount(), 0u);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
145
tests/Core/UI/test_ui_flat_hierarchy_helpers.cpp
Normal file
145
tests/Core/UI/test_ui_flat_hierarchy_helpers.cpp
Normal file
@@ -0,0 +1,145 @@
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <XCEngine/UI/Widgets/UIFlatHierarchyHelpers.h>
|
||||
|
||||
#include <array>
|
||||
#include <unordered_set>
|
||||
#include <vector>
|
||||
|
||||
namespace {
|
||||
|
||||
using XCEngine::UI::Widgets::kInvalidUIFlatHierarchyItemOffset;
|
||||
using XCEngine::UI::Widgets::UIFlatHierarchyFindFirstVisibleChildOffset;
|
||||
using XCEngine::UI::Widgets::UIFlatHierarchyFindParentOffset;
|
||||
using XCEngine::UI::Widgets::UIFlatHierarchyHasChildren;
|
||||
using XCEngine::UI::Widgets::UIFlatHierarchyIsVisible;
|
||||
|
||||
struct FlatHierarchyItem {
|
||||
float depth = 0.0f;
|
||||
};
|
||||
|
||||
TEST(UIFlatHierarchyHelpersTest, HasChildrenAndParentResolutionTrackIndentedBranches) {
|
||||
const std::array<FlatHierarchyItem, 5> items = {{
|
||||
{ 0.0f },
|
||||
{ 1.0f },
|
||||
{ 2.0f },
|
||||
{ 1.0f },
|
||||
{ 0.0f },
|
||||
}};
|
||||
const std::vector<std::size_t> itemIndices = { 0u, 1u, 2u, 3u, 4u };
|
||||
|
||||
const auto resolveDepth = [&items](std::size_t itemIndex) {
|
||||
return items[itemIndex].depth;
|
||||
};
|
||||
|
||||
EXPECT_TRUE(UIFlatHierarchyHasChildren(itemIndices, 0u, resolveDepth));
|
||||
EXPECT_TRUE(UIFlatHierarchyHasChildren(itemIndices, 1u, resolveDepth));
|
||||
EXPECT_FALSE(UIFlatHierarchyHasChildren(itemIndices, 2u, resolveDepth));
|
||||
EXPECT_FALSE(UIFlatHierarchyHasChildren(itemIndices, 3u, resolveDepth));
|
||||
EXPECT_FALSE(UIFlatHierarchyHasChildren(itemIndices, 4u, resolveDepth));
|
||||
|
||||
EXPECT_EQ(
|
||||
UIFlatHierarchyFindParentOffset(itemIndices, 0u, resolveDepth),
|
||||
kInvalidUIFlatHierarchyItemOffset);
|
||||
EXPECT_EQ(UIFlatHierarchyFindParentOffset(itemIndices, 1u, resolveDepth), 0u);
|
||||
EXPECT_EQ(UIFlatHierarchyFindParentOffset(itemIndices, 2u, resolveDepth), 1u);
|
||||
EXPECT_EQ(UIFlatHierarchyFindParentOffset(itemIndices, 3u, resolveDepth), 0u);
|
||||
EXPECT_EQ(
|
||||
UIFlatHierarchyFindParentOffset(itemIndices, 99u, resolveDepth),
|
||||
kInvalidUIFlatHierarchyItemOffset);
|
||||
}
|
||||
|
||||
TEST(UIFlatHierarchyHelpersTest, VisibilityFollowsCollapsedAncestorStateAcrossDepthTransitions) {
|
||||
const std::array<FlatHierarchyItem, 4> items = {{
|
||||
{ 0.0f },
|
||||
{ 1.0f },
|
||||
{ 2.0f },
|
||||
{ 1.0f },
|
||||
}};
|
||||
const std::vector<std::size_t> itemIndices = { 0u, 1u, 2u, 3u };
|
||||
|
||||
const auto resolveDepth = [&items](std::size_t itemIndex) {
|
||||
return items[itemIndex].depth;
|
||||
};
|
||||
|
||||
std::unordered_set<std::size_t> expandedItems = { 0u };
|
||||
const auto isExpanded = [&expandedItems](std::size_t itemIndex) {
|
||||
return expandedItems.contains(itemIndex);
|
||||
};
|
||||
|
||||
EXPECT_TRUE(UIFlatHierarchyIsVisible(itemIndices, 0u, resolveDepth, isExpanded));
|
||||
EXPECT_TRUE(UIFlatHierarchyIsVisible(itemIndices, 1u, resolveDepth, isExpanded));
|
||||
EXPECT_FALSE(UIFlatHierarchyIsVisible(itemIndices, 2u, resolveDepth, isExpanded));
|
||||
EXPECT_TRUE(UIFlatHierarchyIsVisible(itemIndices, 3u, resolveDepth, isExpanded));
|
||||
|
||||
expandedItems.insert(1u);
|
||||
EXPECT_TRUE(UIFlatHierarchyIsVisible(itemIndices, 2u, resolveDepth, isExpanded));
|
||||
|
||||
expandedItems.clear();
|
||||
EXPECT_FALSE(UIFlatHierarchyIsVisible(itemIndices, 1u, resolveDepth, isExpanded));
|
||||
EXPECT_FALSE(UIFlatHierarchyIsVisible(itemIndices, 2u, resolveDepth, isExpanded));
|
||||
}
|
||||
|
||||
TEST(UIFlatHierarchyHelpersTest, FirstVisibleChildSkipsCollapsedDescendantsUntilExpanded) {
|
||||
const std::array<FlatHierarchyItem, 4> items = {{
|
||||
{ 0.0f },
|
||||
{ 1.0f },
|
||||
{ 2.0f },
|
||||
{ 1.0f },
|
||||
}};
|
||||
const std::vector<std::size_t> itemIndices = { 0u, 1u, 2u, 3u };
|
||||
|
||||
const auto resolveDepth = [&items](std::size_t itemIndex) {
|
||||
return items[itemIndex].depth;
|
||||
};
|
||||
|
||||
std::unordered_set<std::size_t> expandedItems = { 0u };
|
||||
const auto isExpanded = [&expandedItems](std::size_t itemIndex) {
|
||||
return expandedItems.contains(itemIndex);
|
||||
};
|
||||
const auto isVisible = [&itemIndices, &resolveDepth, &isExpanded](std::size_t itemIndex) {
|
||||
for (std::size_t itemOffset = 0; itemOffset < itemIndices.size(); ++itemOffset) {
|
||||
if (itemIndices[itemOffset] == itemIndex) {
|
||||
return UIFlatHierarchyIsVisible(itemIndices, itemOffset, resolveDepth, isExpanded);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
};
|
||||
|
||||
EXPECT_EQ(
|
||||
UIFlatHierarchyFindFirstVisibleChildOffset(itemIndices, 0u, resolveDepth, isVisible),
|
||||
1u);
|
||||
EXPECT_EQ(
|
||||
UIFlatHierarchyFindFirstVisibleChildOffset(itemIndices, 1u, resolveDepth, isVisible),
|
||||
kInvalidUIFlatHierarchyItemOffset);
|
||||
|
||||
expandedItems.insert(1u);
|
||||
EXPECT_EQ(
|
||||
UIFlatHierarchyFindFirstVisibleChildOffset(itemIndices, 1u, resolveDepth, isVisible),
|
||||
2u);
|
||||
}
|
||||
|
||||
TEST(UIFlatHierarchyHelpersTest, NegativeDepthsClampToRootsForHierarchyQueries) {
|
||||
const std::array<FlatHierarchyItem, 3> items = {{
|
||||
{ -3.0f },
|
||||
{ 1.0f },
|
||||
{ -1.0f },
|
||||
}};
|
||||
const std::vector<std::size_t> itemIndices = { 0u, 1u, 2u };
|
||||
|
||||
const auto resolveDepth = [&items](std::size_t itemIndex) {
|
||||
return items[itemIndex].depth;
|
||||
};
|
||||
const auto isExpanded = [](std::size_t itemIndex) {
|
||||
return itemIndex == 0u;
|
||||
};
|
||||
|
||||
EXPECT_TRUE(UIFlatHierarchyHasChildren(itemIndices, 0u, resolveDepth));
|
||||
EXPECT_EQ(UIFlatHierarchyFindParentOffset(itemIndices, 1u, resolveDepth), 0u);
|
||||
EXPECT_EQ(
|
||||
UIFlatHierarchyFindParentOffset(itemIndices, 2u, resolveDepth),
|
||||
kInvalidUIFlatHierarchyItemOffset);
|
||||
EXPECT_TRUE(UIFlatHierarchyIsVisible(itemIndices, 2u, resolveDepth, isExpanded));
|
||||
}
|
||||
|
||||
} // namespace
|
||||
Reference in New Issue
Block a user