Skip to content

Commit c3fa271

Browse files
committed
Do not call UpdateFixedBounds in constructor of Widget
1 parent 7d519ea commit c3fa271

File tree

4 files changed

+64
-32
lines changed

4 files changed

+64
-32
lines changed

LibGUI/include/Lemon/GUI/Model.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ class DataModel {
5252
///
5353
/// \return Column name
5454
/////////////////////////////
55-
virtual const std::string& ColumnName(int column) const = 0;
55+
virtual const char* ColumnName(int column) const = 0;
5656

5757
/////////////////////////////
5858
/// \brief Sort by specified column (optional)

LibGUI/include/Lemon/GUI/Widgets.h

Lines changed: 7 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -47,13 +47,7 @@ class Widget {
4747
inline Widget* GetParent() { return parent; }
4848

4949
virtual void SetLayout(LayoutSize newSizeX, LayoutSize newSizeY, WidgetAlignment newAlign = WAlignLeft,
50-
WidgetAlignment newAlignVert = WAlignTop) {
51-
sizeX = newSizeX;
52-
sizeY = newSizeY;
53-
align = newAlign;
54-
verticalAlign = newAlignVert;
55-
UpdateFixedBounds();
56-
};
50+
WidgetAlignment newAlignVert = WAlignTop);
5751

5852
virtual void Paint(surface_t* surface);
5953

@@ -91,9 +85,6 @@ class Widget {
9185
Widget* parent = nullptr;
9286
Window* window = nullptr;
9387

94-
short layoutSizeX = LayoutSize::Fixed;
95-
short layoutSizeY = LayoutSize::Fixed;
96-
9788
rect_t bounds;
9889
rect_t fixedBounds;
9990

@@ -145,6 +136,10 @@ class LayoutContainer : public Container {
145136
int xPadding = 2;
146137
int yPadding = 2;
147138

139+
// Whether or not the LayoutContainer should expand the Widgets
140+
// to fill the width of the container
141+
bool xFill = false;
142+
148143
LayoutContainer(rect_t bounds, vector2i_t itemSize);
149144

150145
void AddWidget(Widget* w);
@@ -218,6 +213,8 @@ class Button : public Widget {
218213

219214
Button(const char* _label, rect_t _bounds);
220215

216+
void SetLabel(const char* _label);
217+
221218
virtual void Paint(surface_t* surface);
222219
virtual void OnMouseDown(vector2i_t mousePos);
223220
virtual void OnMouseUp(vector2i_t mousePos);

LibGUI/src/Widgets.cpp

Lines changed: 33 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -20,12 +20,19 @@ Widget::Widget(rect_t bounds, LayoutSize newSizeX, LayoutSize newSizeY) {
2020

2121
sizeX = newSizeX;
2222
sizeY = newSizeY;
23-
24-
UpdateFixedBounds();
2523
}
2624

2725
Widget::~Widget() {}
2826

27+
void Widget::SetLayout(LayoutSize newSizeX, LayoutSize newSizeY, WidgetAlignment newAlign,
28+
WidgetAlignment newAlignVert) {
29+
sizeX = newSizeX;
30+
sizeY = newSizeY;
31+
align = newAlign;
32+
verticalAlign = newAlignVert;
33+
UpdateFixedBounds();
34+
};
35+
2936
void Widget::Paint(__attribute__((unused)) surface_t* surface) {}
3037

3138
void Widget::OnMouseEnter(vector2i_t mousePos) { OnMouseMove(mousePos); }
@@ -258,7 +265,7 @@ void Container::UpdateFixedBounds() {
258265
//////////////////////////
259266
// LayoutContainer
260267
//////////////////////////
261-
LayoutContainer::LayoutContainer(rect_t bounds, vector2i_t itemSize) : Container(bounds) { this->itemSize = itemSize; }
268+
LayoutContainer::LayoutContainer(rect_t bounds, vector2i_t minItemSize) : Container(bounds) { this->itemSize = minItemSize; }
262269

263270
void LayoutContainer::AddWidget(Widget* w) {
264271
Container::AddWidget(w);
@@ -275,20 +282,33 @@ void LayoutContainer::RemoveWidget(Widget* w) {
275282
void LayoutContainer::UpdateFixedBounds() {
276283
Widget::UpdateFixedBounds();
277284

285+
if(!children.size()) {
286+
return;
287+
}
288+
278289
vector2i_t pos = {xPadding, yPadding};
279290
isOverflowing = false;
280291

292+
int itemWidth = itemSize.x;
293+
int itemHeight = itemSize.y;
294+
int itemsPerRow = (fixedBounds.width - xPadding) / (itemSize.x + xPadding);
295+
296+
// Fill the width of the container if requested
297+
if(xFill && itemsPerRow >= (int)children.size()) {
298+
itemWidth = ((fixedBounds.width - xPadding) / children.size()) - xPadding;
299+
}
300+
281301
for (Widget* w : children) {
282-
w->SetBounds({pos, itemSize});
302+
w->SetBounds({pos, {itemWidth, itemHeight}});
283303
w->SetLayout(LayoutSize::Fixed, LayoutSize::Fixed, WidgetAlignment::WAlignLeft);
284304

285305
w->UpdateFixedBounds();
286306

287-
pos.x += itemSize.x + xPadding;
307+
pos.x += itemWidth + xPadding;
288308

289-
if (pos.x + itemSize.x > fixedBounds.width) {
309+
if (pos.x + itemWidth > fixedBounds.width) {
290310
pos.x = xPadding;
291-
pos.y += itemSize.y + yPadding;
311+
pos.y += itemHeight + yPadding;
292312
}
293313
}
294314

@@ -304,6 +324,11 @@ Button::Button(const char* _label, rect_t _bounds) : Widget(_bounds) {
304324
labelLength = Graphics::GetTextLength(label.c_str());
305325
}
306326

327+
void Button::SetLabel(const char* _label) {
328+
label = _label;
329+
labelLength = Graphics::GetTextLength(label.c_str());
330+
}
331+
307332
void Button::DrawButtonLabel(surface_t* surface) {
308333
rgba_colour_t colour;
309334
vector2i_t btnPos = fixedBounds.pos;
@@ -814,7 +839,7 @@ void ListView::Paint(surface_t* surface) {
814839
int xPos = fixedBounds.x;
815840
for (int i = 0; i < model->ColumnCount(); i++) {
816841
if (displayColumnNames) {
817-
Graphics::DrawString(model->ColumnName(i).c_str(), xPos + 4, fixedBounds.y + 4, textColour.r, textColour.g,
842+
Graphics::DrawString(model->ColumnName(i), xPos + 4, fixedBounds.y + 4, textColour.r, textColour.g,
818843
textColour.b, surface);
819844

820845
Graphics::DrawRect(xPos, fixedBounds.y + 1, 1, columnDisplayHeight - 2, textColour, surface); // Divider

LibGUI/src/Window.cpp

Lines changed: 23 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
#include <Lemon/Core/JSON.h>
22
#include <Lemon/Core/SharedMemory.h>
3+
#include <Lemon/Core/Logger.h>
34
#include <Lemon/GUI/Window.h>
45

56
#include <Lemon/GUI/WindowServer.h>
@@ -12,11 +13,18 @@
1213
namespace Lemon::GUI {
1314
Window::Window(const char* title, vector2i_t size, uint32_t flags, int type, vector2i_t pos)
1415
: rootContainer({{0, 0}, size}), m_flags(flags), m_windowType(type) {
15-
rootContainer.SetWindow(this);
16-
1716
WindowServer* server = WindowServer::Instance();
18-
rootContainer.background = Theme::Current().ColourBackground();
17+
if(!server) {
18+
Logger::Error("Failed to connect to lemonwm!");
19+
exit(1);
20+
}
21+
22+
if(m_windowType == WindowType::GUI) {
23+
rootContainer.SetWindow(this);
24+
rootContainer.background = Theme::Current().ColourBackground();
25+
}
1926

27+
assert(server);
2028
auto response = server->CreateWindow(pos.x, pos.y, size.x, size.y, flags, title);
2129

2230
m_windowBufferKey = response.bufferKey;
@@ -56,13 +64,15 @@ void Window::Relocate(vector2i_t pos) { WindowServer::Instance()->Relocate(m_win
5664
void Window::Resize(vector2i_t size) {
5765
Lemon::UnmapSharedMemory(m_windowBufferInfo, m_windowBufferKey);
5866

59-
if (menuBar) {
60-
rootContainer.SetBounds({{0, WINDOW_MENUBAR_HEIGHT}, {size.x, size.y - WINDOW_MENUBAR_HEIGHT}});
61-
} else {
62-
rootContainer.SetBounds({{0, 0}, size});
63-
}
67+
if(m_windowType == WindowType::GUI) {
68+
if (menuBar) {
69+
rootContainer.SetBounds({{0, WINDOW_MENUBAR_HEIGHT}, {size.x, size.y - WINDOW_MENUBAR_HEIGHT}});
70+
} else {
71+
rootContainer.SetBounds({{0, 0}, size});
72+
}
6473

65-
rootContainer.UpdateFixedBounds();
74+
rootContainer.UpdateFixedBounds();
75+
}
6676

6777
m_windowBufferKey = WindowServer::Instance()->Resize(m_windowID, size.x, size.y).bufferKey;
6878
if (m_windowBufferKey <= 0) {
@@ -93,8 +103,8 @@ void Window::UpdateFlags(uint32_t flags) {
93103
}
94104

95105
void Window::SwapBuffers() {
96-
if (m_windowBufferInfo->drawing)
97-
return;
106+
while (m_windowBufferInfo->drawing)
107+
; // WM is currently drawing the other buffer
98108

99109
if (surface.buffer == m_buffer1) {
100110
m_windowBufferInfo->currentBuffer = 0;
@@ -137,13 +147,13 @@ bool Window::PollEvent(LemonEvent& ev) {
137147

138148
void Window::GUIPollEvents() {
139149
LemonEvent ev;
140-
while (PollEvent(ev)) {
150+
while (!closed && PollEvent(ev)) {
141151
// If the handler returns true, the event is not processed.
142152
auto handler = m_eventHandlers.find(ev.event);
143153
if (handler != m_eventHandlers.end() && handler->second(ev)) {
144154
continue;
145155
}
146-
156+
147157
GUIHandleEvent(ev);
148158
}
149159

0 commit comments

Comments
 (0)