Slight changes to UI

This commit is contained in:
Yousef Khadadeh 2026-05-13 19:56:14 +03:00
parent 4774f1ee94
commit a533494b3a
12 changed files with 129 additions and 21 deletions

View file

@ -108,8 +108,8 @@ void text_button_sized(GUIManager& gui, const char* id, std::string_view text, C
SelectableButton* svg_icon_button(GUIManager& gui, const char* id, const std::string& svgPath, const SVGButtonOptions& options) {
SelectableButton::Data d = selectable_button_options_to_data(options);
d.innerContent = [&gui, &svgPath] (const SelectableButton::InnerContentCallbackParameters& p) {
gui.element<SVGIcon>("icon", svgPath, p.isSelected || p.isHovering || p.isHeld);
d.innerContent = [&gui, &svgPath, &options] (const SelectableButton::InnerContentCallbackParameters& p) {
gui.element<SVGIcon>("icon", svgPath, p.isSelected || p.isHovering || p.isHeld, options.drawType == SelectableButton::DrawType::FILLED_INVERSE);
};
SelectableButton* toRet;
CLAY_AUTO_ID({.layout = {.sizing = {.width = CLAY_SIZING_FIXED(options.size), .height = CLAY_SIZING_FIXED(options.size) } } }) {

View file

@ -31,7 +31,7 @@ void CheckBox::layout(const Clay_ElementId& id, const std::function<bool()>& isT
this->isTicked = isTicked;
this->onClick = onClick;
float size = gui.io.isTouchDevice ? 25 : 15;
float size = 20;
CLAY(id, {
.layout = {
.sizing = {.width = CLAY_SIZING_FIXED(size), .height = CLAY_SIZING_FIXED(size)}

View file

@ -29,7 +29,7 @@ void RadioButton::layout(const Clay_ElementId& id, const std::function<bool()>&
this->onClick = onClick;
this->isTicked = isTicked;
float size = gui.io.isTouchDevice ? 25 : 20;
float size = 20;
CLAY(id, {
.layout = {
.sizing = {.width = CLAY_SIZING_FIXED(size), .height = CLAY_SIZING_FIXED(size)}

View file

@ -29,7 +29,7 @@ namespace GUIStuff {
SVGIcon::SVGIcon(GUIManager& gui):
Element(gui) {}
void SVGIcon::layout(const Clay_ElementId& id, const std::string& newSvgPath, bool newIsHighlighted) {
void SVGIcon::layout(const Clay_ElementId& id, const std::string& newSvgPath, bool newIsHighlighted, bool newInverse) {
bool redraw = false;
auto& io = gui.io;
@ -42,7 +42,9 @@ void SVGIcon::layout(const Clay_ElementId& id, const std::string& newSvgPath, bo
}
redraw |= highlighted != newIsHighlighted;
redraw |= inverse != newInverse;
highlighted = newIsHighlighted;
inverse = newInverse;
if(redraw)
gui.invalidate_draw_element(this);
@ -66,7 +68,10 @@ void SVGIcon::clay_draw(SkCanvas* canvas, UpdateInputData& io, Clay_RenderComman
SkRect r = SkRect::MakeXYWH(0.0f, 0.0f, bb.width(), bb.height());
canvas->clipRect(r);
SkPaint blendingPaint;
blendingPaint.setColorFilter(SkColorFilters::Blend(highlighted ? io.theme->frontColor1 : io.theme->frontColor2, SkColorSpace::MakeSRGB(), SkBlendMode::kSrcIn));
if(inverse)
blendingPaint.setColorFilter(SkColorFilters::Blend(highlighted ? io.theme->backColor1 : io.theme->backColor2, SkColorSpace::MakeSRGB(), SkBlendMode::kSrcIn));
else
blendingPaint.setColorFilter(SkColorFilters::Blend(highlighted ? io.theme->frontColor1 : io.theme->frontColor2, SkColorSpace::MakeSRGB(), SkBlendMode::kSrcIn));
canvas->saveLayer(r, &blendingPaint);
canvas->scale(bb.width() / svgDom->containerSize().width(), bb.height() / svgDom->containerSize().height());
svgDom->render(canvas);

View file

@ -24,9 +24,10 @@ namespace GUIStuff {
class SVGIcon : public Element {
public:
SVGIcon(GUIManager& gui);
void layout(const Clay_ElementId& id, const std::string& newSvgPath, bool newIsHighlighted = false);
void layout(const Clay_ElementId& id, const std::string& newSvgPath, bool newIsHighlighted = false, bool newInverse = false);
virtual void clay_draw(SkCanvas* canvas, UpdateInputData& io, Clay_RenderCommand* command, bool skiaAA) override;
private:
bool inverse;
bool highlighted;
sk_sp<SkSVGDOM> svgDom;
};

View file

@ -152,6 +152,10 @@ void TreeListing::layout(const Clay_ElementId& id, const Data& newDisplayData) {
}
}
d.drawObjGUI(objInfo.objIndex);
// Gap for scroll bar
CLAY_AUTO_ID({
.layout = {.sizing = {.width = CLAY_SIZING_FIT(15), .height = CLAY_SIZING_GROW(0)}}
}) {}
}
}
}, LayoutElement::Callbacks {

View file

@ -328,6 +328,10 @@ void GridManager::setup_list_gui(const std::function<void()>& onStartModify) {
list_button("delete trash", "data/icons/trash.svg", [&, i] {
main.world->gridMan.remove_grid(i);
});
// Gap for scroll bar
CLAY_AUTO_ID({
.layout = {.sizing = {.width = CLAY_SIZING_FIT(15), .height = CLAY_SIZING_GROW(0)}}
}) {}
}
}
}, LayoutElement::Callbacks {

View file

@ -241,7 +241,7 @@ void FileSelectScreen::create_file_button() {
CLAY(lId, {
.layout = {.sizing = {.width = CLAY_SIZING_FIT(0), .height = CLAY_SIZING_FIT(0)}},
.floating = {
.offset = {-5, -5},
.offset = {-25, -25},
.zIndex = gui.get_z_index(),
.attachPoints = {
.element = CLAY_ATTACH_POINT_RIGHT_BOTTOM,
@ -251,6 +251,8 @@ void FileSelectScreen::create_file_button() {
}
}) {
svg_icon_button(gui, "add button", "data/icons/plus.svg", {
.drawType = SelectableButton::DrawType::FILLED_INVERSE,
.size = 40.0f,
.onClick = [&] {
CustomEvents::emit_event<CustomEvents::OpenInfiniPaintFileEvent>({
.isClient = false,

View file

@ -83,17 +83,39 @@ void PhoneDrawingProgramScreen::main_display() {
.layoutDirection = CLAY_TOP_TO_BOTTOM
},
}) {
top_toolbar();
top_toolbar_settings_popup();
CLAY_AUTO_ID({
.layout = {.sizing = {.width = CLAY_SIZING_GROW(0), .height = CLAY_SIZING_GROW(0)}}
}) {}
bottom_toolbar();
if(hideGUI)
hidden_gui();
else {
top_toolbar();
top_toolbar_settings_popup();
CLAY_AUTO_ID({
.layout = {.sizing = {.width = CLAY_SIZING_GROW(0), .height = CLAY_SIZING_GROW(0)}}
}) {}
bottom_toolbar();
}
if(!main.world->drawProg.layerMan.is_a_layer_being_edited())
center_message("Select layer to edit message", "Select a layer to edit");
}
}
void PhoneDrawingProgramScreen::hidden_gui() {
auto& gui = main.g.gui;
window_fill_side_bar(gui, WindowFillSideBarConfig{
.dir = WindowFillSideBarConfig::Direction::TOP
}, [&] {
CLAY_AUTO_ID({
.layout = {.sizing = {.width = CLAY_SIZING_GROW(0)}}
});
svg_icon_button(gui, "show gui button", "data/icons/eyeopen.svg", {
.isSelected = true,
.onClick = [&] {
hideGUI = false;
}
});
});
}
void PhoneDrawingProgramScreen::top_toolbar_settings_popup() {
auto& gui = main.g.gui;
auto& io = gui.io;
@ -183,6 +205,42 @@ void PhoneDrawingProgramScreen::top_toolbar_settings_popup() {
});
break;
}
case TopToolbarSettingsPopup::HOST: {
gui.set_z_index(gui.get_z_index() + 20, [&] {
gui.element<LayoutElement>("host lobby menu", [&] (LayoutElement*, const Clay_ElementId& lId) {
Vector2f popupSize = {
std::clamp(gui.io.safeWindowRect.width() - 10.0f, 20.0f, 300.0f),
std::clamp(gui.io.safeWindowRect.height() - 40.0f, 50.0f, 600.0f)
};
CLAY(lId, {
.layout = {
.sizing = {.width = CLAY_SIZING_FIT(popupSize.x()), .height = CLAY_SIZING_FIT(0, popupSize.y()) },
.padding = CLAY_PADDING_ALL(io.theme->padding1),
.childGap = io.theme->childGap1,
.childAlignment = { .x = CLAY_ALIGN_X_CENTER, .y = CLAY_ALIGN_Y_TOP},
.layoutDirection = CLAY_TOP_TO_BOTTOM
},
.backgroundColor = convert_vec4<Clay_Color>(io.theme->backColor1),
.cornerRadius = CLAY_CORNER_RADIUS(io.theme->windowCorners1),
.floating = {.offset = {.x = 0, .y = static_cast<float>(io.theme->padding1)}, .zIndex = gui.get_z_index(), .attachPoints = {.element = CLAY_ATTACH_POINT_RIGHT_TOP, .parent = CLAY_ATTACH_POINT_RIGHT_BOTTOM}, .attachTo = CLAY_ATTACH_TO_PARENT}
}) {
text_label_centered(gui, "Host");
input_text_field(gui, "lobby", "Lobby", &serverToConnectTo, {
.immutable = true
});
text_button(gui, "Host button", "Copy & Host", {
.wide = true,
.onClick = [&] {
main.input.set_clipboard_str(serverToConnectTo);
main.world->start_hosting(serverToConnectTo, serverLocalID);
topToolbarSettingsPopup = TopToolbarSettingsPopup::NONE;
}
});
}
});
});
break;
}
}
}
@ -264,6 +322,14 @@ void PhoneDrawingProgramScreen::top_toolbar_remaining_area() {
topToolbarSettingsPopup = topToolbarSettingsPopup == TopToolbarSettingsPopup::GRIDS ? TopToolbarSettingsPopup::NONE : TopToolbarSettingsPopup::GRIDS;
}
},
TopToolbarRemainingAreaButton{
.name = "Hide Toolbars",
.svgPath = "data/icons/eyeopen.svg",
.isSelected = false,
.onClick = [&] {
hideGUI = true;
}
},
};
gui.element<LayoutElement>("remaining area", [&](LayoutElement* l, const Clay_ElementId& lId) {
CLAY(lId, {
@ -309,6 +375,7 @@ void PhoneDrawingProgramScreen::top_toolbar_remaining_area() {
});
Element* e = svg_icon_button(gui, "Hidden buttons", "data/icons/RemixIcon/more-2-fill.svg", {
.drawType = SelectableButton::DrawType::TRANSPARENT_ALL,
.isSelected = topToolbarSettingsPopup == TopToolbarSettingsPopup::HIDDEN_BUTTONS,
.onClick = [&] {
topToolbarSettingsPopup = topToolbarSettingsPopup == TopToolbarSettingsPopup::HIDDEN_BUTTONS ? TopToolbarSettingsPopup::NONE : TopToolbarSettingsPopup::HIDDEN_BUTTONS;
}
@ -351,6 +418,16 @@ void PhoneDrawingProgramScreen::top_toolbar_hidden_button_popup(GUIStuff::Elemen
}
});
l.emplace_back(TopToolbarRemainingAreaButton{
.name = "Host",
.svgPath = "data/icons/network.svg",
.onClick = [&] {
serverLocalID = NetLibrary::get_random_server_local_id();
serverToConnectTo = NetLibrary::get_global_id() + serverLocalID;
topToolbarSettingsPopup = topToolbarSettingsPopup == TopToolbarSettingsPopup::HOST ? TopToolbarSettingsPopup::NONE : TopToolbarSettingsPopup::HOST;
}
});
gui.set_z_index(gui.get_z_index() + 20, [&] {
dropdown_many_element_popup_layout(gui, "top toolbar hidden button popup", {
.button = b,
@ -935,10 +1012,16 @@ void PhoneDrawingProgramScreen::bottom_extra_toolbar_gui() {
}
void PhoneDrawingProgramScreen::input_global_back_button_callback() {
main.world->save_to_file(main.world->filePath);
main.set_tab_to_close(main.world.get());
main.g.gui.set_to_layout();
main.set_screen([&] (std::unique_ptr<Screen>) { return std::make_unique<FileSelectScreen>(main); });
if(hideGUI) {
hideGUI = false;
main.g.gui.set_to_layout();
}
else {
main.world->save_to_file(main.world->filePath);
main.set_tab_to_close(main.world.get());
main.g.gui.set_to_layout();
main.set_screen([&] (std::unique_ptr<Screen>) { return std::make_unique<FileSelectScreen>(main); });
}
}
void PhoneDrawingProgramScreen::input_app_about_to_go_to_background_callback() {

View file

@ -72,13 +72,17 @@ class PhoneDrawingProgramScreen : public DrawingProgramScreen {
HIDDEN_BUTTONS,
BOOKMARKS,
LAYERS,
GRIDS
GRIDS,
HOST
} topToolbarSettingsPopup = TopToolbarSettingsPopup::NONE;
bool hideGUI = false;
Vector4f backgroundColorTemporary;
Vector4f* colorPickerPtr = nullptr;
ColorSelectorData colorPickerData;
void hidden_gui();
void center_message(const char* id, const std::string& m);
void default_bottom_toolbar();
void bottom_toolbar_gui();
@ -91,4 +95,7 @@ class PhoneDrawingProgramScreen : public DrawingProgramScreen {
void bottom_toolbar();
void main_display();
void tool_settings_popup();
std::string serverToConnectTo;
std::string serverLocalID;
};

View file

@ -1428,7 +1428,9 @@ void Toolbar::options_menu() {
switch(optionsMenuType) {
case HOST_MENU: {
center_obstructing_window_gui("host menu", CLAY_SIZING_FIT(650), CLAY_SIZING_FIT(0), [&] {
input_text_field(gui, "lobby", "Lobby", &serverToConnectTo);
input_text_field(gui, "lobby", "Lobby", &serverToConnectTo, {
.immutable = true
});
left_to_right_line_layout(gui, [&]() {
text_button_wide("copy lobby address", "Copy Lobby Address", [&] {
main.input.set_clipboard_str(serverToConnectTo);

View file

@ -216,7 +216,7 @@ void initialize_sdl(MainStruct& mS, int wWidth, int wHeight) {
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_VERSION_STRING, VersionConstants::CURRENT_VERSION_STRING.c_str());
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_IDENTIFIER_STRING, "com.infinipaint.infinipaint");
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_CREATOR_STRING, "Yousef Khadadeh (ErrorAtLine0)");
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_COPYRIGHT_STRING, "Copyright (c) 2026 Yousef Khadadeh");
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_COPYRIGHT_STRING, "Copyright (C) 2025-2026 Yousef Khadadeh");
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_URL_STRING, "https://infinipaint.com/");
SDL_SetAppMetadataProperty(SDL_PROP_APP_METADATA_TYPE_STRING, "application");