Skip to content

Commit a31fc53

Browse files
committed
Add tests for MultiSplitter child window initial positioning.
1 parent 688deae commit a31fc53

File tree

3 files changed

+247
-104
lines changed

3 files changed

+247
-104
lines changed

src/MultiSplitter.cpp

Lines changed: 28 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -48,12 +48,12 @@ REHex::MultiSplitter::~MultiSplitter()
4848
RemoveAllChildren();
4949
}
5050

51-
void REHex::MultiSplitter::AddFirst(wxWindow *window)
51+
void REHex::MultiSplitter::AddFirst(wxWindow *window, float weight)
5252
{
5353
wxASSERT_MSG((window->GetParent() == this), "Windows added to a MultiSplitter must be direct children");
5454

5555
assert(!m_cells);
56-
m_cells.reset(new Cell(this, NULL, window));
56+
m_cells.reset(new Cell(this, NULL, window, weight));
5757

5858
m_cells->Resize(GetClientSize());
5959

@@ -62,7 +62,7 @@ void REHex::MultiSplitter::AddFirst(wxWindow *window)
6262
window->Bind(wxEVT_LEFT_DOWN, &REHex::MultiSplitter::OnChildMouseLeftDown, this);
6363
}
6464

65-
void REHex::MultiSplitter::AddLeftOf(wxWindow *window, wxWindow *base)
65+
void REHex::MultiSplitter::AddLeftOf(wxWindow *window, wxWindow *base, float weight)
6666
{
6767
wxASSERT_MSG((window->GetParent() == this), "Windows added to a MultiSplitter must be direct children");
6868
wxASSERT_MSG((window != base), "window and base passed to REHex::MultiSplitter::AddLeftOf() must be different windows");
@@ -87,7 +87,7 @@ void REHex::MultiSplitter::AddLeftOf(wxWindow *window, wxWindow *base)
8787
assert(base_cell != NULL);
8888
}
8989

90-
base_cell->SplitVertically(window, base);
90+
base_cell->SplitVertically(window, base, weight);
9191

9292
if(window_cell == NULL)
9393
{
@@ -97,7 +97,7 @@ void REHex::MultiSplitter::AddLeftOf(wxWindow *window, wxWindow *base)
9797
}
9898
}
9999

100-
void REHex::MultiSplitter::AddRightOf(wxWindow *window, wxWindow *base)
100+
void REHex::MultiSplitter::AddRightOf(wxWindow *window, wxWindow *base, float weight)
101101
{
102102
wxASSERT_MSG((window->GetParent() == this), "Windows added to a MultiSplitter must be direct children");
103103
wxASSERT_MSG((window != base), "window and base passed to REHex::MultiSplitter::AddRightOf() must be different windows");
@@ -122,7 +122,7 @@ void REHex::MultiSplitter::AddRightOf(wxWindow *window, wxWindow *base)
122122
assert(base_cell != NULL);
123123
}
124124

125-
base_cell->SplitVertically(base, window);
125+
base_cell->SplitVertically(base, window, weight);
126126

127127
if(window_cell == NULL)
128128
{
@@ -132,7 +132,7 @@ void REHex::MultiSplitter::AddRightOf(wxWindow *window, wxWindow *base)
132132
}
133133
}
134134

135-
void REHex::MultiSplitter::AddAbove(wxWindow *window, wxWindow *base)
135+
void REHex::MultiSplitter::AddAbove(wxWindow *window, wxWindow *base, float weight)
136136
{
137137
wxASSERT_MSG((window->GetParent() == this), "Windows added to a MultiSplitter must be direct children");
138138
wxASSERT_MSG((window != base), "window and base passed to REHex::MultiSplitter::AddAbove() must be different windows");
@@ -157,7 +157,7 @@ void REHex::MultiSplitter::AddAbove(wxWindow *window, wxWindow *base)
157157
assert(base_cell != NULL);
158158
}
159159

160-
base_cell->SplitHorizontally(window, base);
160+
base_cell->SplitHorizontally(window, base, weight);
161161

162162
if(window_cell == NULL)
163163
{
@@ -167,7 +167,7 @@ void REHex::MultiSplitter::AddAbove(wxWindow *window, wxWindow *base)
167167
}
168168
}
169169

170-
void REHex::MultiSplitter::AddBelow(wxWindow *window, wxWindow *base)
170+
void REHex::MultiSplitter::AddBelow(wxWindow *window, wxWindow *base, float weight)
171171
{
172172
wxASSERT_MSG((window->GetParent() == this), "Windows added to a MultiSplitter must be direct children");
173173
wxASSERT_MSG((window != base), "window and base passed to REHex::MultiSplitter::AddBelow() must be different windows");
@@ -192,7 +192,7 @@ void REHex::MultiSplitter::AddBelow(wxWindow *window, wxWindow *base)
192192
assert(base_cell != NULL);
193193
}
194194

195-
base_cell->SplitHorizontally(base, window);
195+
base_cell->SplitHorizontally(base, window, weight);
196196

197197
if(window_cell == NULL)
198198
{
@@ -740,10 +740,10 @@ void REHex::MultiSplitter::OnChildMouseLeftDown(wxMouseEvent &event)
740740
event.Skip();
741741
}
742742

743-
REHex::MultiSplitter::Cell::Cell(const MultiSplitter *splitter, Cell *parent, wxWindow *window):
743+
REHex::MultiSplitter::Cell::Cell(const MultiSplitter *splitter, Cell *parent, wxWindow *window, float weight):
744744
m_splitter(splitter),
745745
m_parent(parent),
746-
m_weight(1.0f),
746+
m_weight(weight),
747747
m_drag_border_left(0),
748748
m_drag_border_right(0),
749749
m_drag_border_top(0),
@@ -1420,13 +1420,13 @@ void REHex::MultiSplitter::Cell::MoveSplitter(const wxPoint &point, bool force)
14201420
}
14211421
}
14221422

1423-
void REHex::MultiSplitter::Cell::SplitHorizontally(wxWindow *window_top, wxWindow *window_bottom)
1423+
void REHex::MultiSplitter::Cell::SplitHorizontally(wxWindow *window_top, wxWindow *window_bottom, float new_window_weight)
14241424
{
14251425
assert(!m_left && !m_right && !m_top && !m_bottom);
14261426
assert(m_window == window_top || m_window == window_bottom);
14271427

1428-
std::unique_ptr<Cell> new_top(new Cell(m_splitter, this, window_top));
1429-
std::unique_ptr<Cell> new_bottom(new Cell(m_splitter, this, window_bottom));
1428+
std::unique_ptr<Cell> new_top(new Cell(m_splitter, this, window_top, new_window_weight));
1429+
std::unique_ptr<Cell> new_bottom(new Cell(m_splitter, this, window_bottom, new_window_weight));
14301430

14311431
m_top = std::move(new_top);
14321432
m_bottom = std::move(new_bottom);
@@ -1441,20 +1441,24 @@ void REHex::MultiSplitter::Cell::SplitHorizontally(wxWindow *window_top, wxWindo
14411441
m_hidden_lt = false;
14421442
m_hidden_rb = false;
14431443

1444-
int t_height = m_rect.height / 2;
1444+
/* Avoid division by zero if both weights are zero. */
1445+
int t_height = m_top->m_weight == m_bottom->m_weight
1446+
? m_rect.height / 2
1447+
: ((float)(m_rect.height) / (m_top->m_weight + m_bottom->m_weight)) * m_top->m_weight;
1448+
14451449
int b_height = m_rect.height - t_height;
14461450

14471451
m_top->Resize(wxRect(m_rect.x, m_rect.y, m_rect.width, t_height));
14481452
m_bottom->Resize(wxRect(m_rect.x, (m_rect.y + t_height), m_rect.width, b_height));
14491453
}
14501454

1451-
void REHex::MultiSplitter::Cell::SplitVertically(wxWindow *window_left, wxWindow *window_right)
1455+
void REHex::MultiSplitter::Cell::SplitVertically(wxWindow *window_left, wxWindow *window_right, float new_window_weight)
14521456
{
14531457
assert(!m_left && !m_right && !m_top && !m_bottom);
14541458
assert(m_window == window_left || m_window == window_right);
14551459

1456-
std::unique_ptr<Cell> new_left(new Cell(m_splitter, this, window_left));
1457-
std::unique_ptr<Cell> new_right(new Cell(m_splitter, this, window_right));
1460+
std::unique_ptr<Cell> new_left(new Cell(m_splitter, this, window_left, new_window_weight));
1461+
std::unique_ptr<Cell> new_right(new Cell(m_splitter, this, window_right, new_window_weight));
14581462

14591463
/* The cell which inherits our window should also inherit the existing weight/etc. */
14601464

@@ -1479,7 +1483,11 @@ void REHex::MultiSplitter::Cell::SplitVertically(wxWindow *window_left, wxWindow
14791483
m_hidden_lt = false;
14801484
m_hidden_rb = false;
14811485

1482-
int l_width = m_rect.width / 2;
1486+
/* Avoid division by zero if both weights are zero. */
1487+
int l_width = m_left->m_weight == m_right->m_weight
1488+
? m_rect.width / 2
1489+
: ((float)(m_rect.width) / (m_left->m_weight + m_right->m_weight)) * m_left->m_weight;
1490+
14831491
int r_width = m_rect.width - l_width;
14841492

14851493
m_left->Resize(wxRect(m_rect.x, m_rect.y, l_width, m_rect.height));

src/MultiSplitter.hpp

Lines changed: 55 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ namespace REHex
7878
bool m_hidden_rb;
7979

8080
public:
81-
Cell(const MultiSplitter *splitter, Cell *parent, wxWindow *window);
81+
Cell(const MultiSplitter *splitter, Cell *parent, wxWindow *window, float weight);
8282

8383
/**
8484
* @brief Set the "weight" of the cell.
@@ -194,7 +194,7 @@ namespace REHex
194194
* this cell and the other one should not be in the wxExSplitter cell
195195
* hierarchy.
196196
*/
197-
void SplitHorizontally(wxWindow *window_top, wxWindow *window_bottom);
197+
void SplitHorizontally(wxWindow *window_top, wxWindow *window_bottom, float new_window_weight);
198198

199199
/**
200200
* @brief Split the cell vertically.
@@ -205,7 +205,7 @@ namespace REHex
205205
* this cell and the other one should not be in the wxExSplitter cell
206206
* hierarchy.
207207
*/
208-
void SplitVertically(wxWindow *window_left, wxWindow *window_right);
208+
void SplitVertically(wxWindow *window_left, wxWindow *window_right, float new_window_weight);
209209

210210
/**
211211
* @brief Remove one of the immediate child cells from a split cell.
@@ -484,11 +484,58 @@ namespace REHex
484484
MultiSplitter(wxWindow *parent);
485485
virtual ~MultiSplitter();
486486

487-
void AddFirst(wxWindow *window);
488-
void AddLeftOf(wxWindow *window, wxWindow *base);
489-
void AddRightOf(wxWindow *window, wxWindow *base);
490-
void AddAbove(wxWindow *window, wxWindow *base);
491-
void AddBelow(wxWindow *window, wxWindow *base);
487+
/**
488+
* @brief Add the first window to the splitter.
489+
*/
490+
void AddFirst(wxWindow *window, float weight = 1.0f);
491+
492+
/**
493+
* @brief Split an existing cell, inserting a new window to the left.
494+
*
495+
* @param window New window to be added to the splitter.
496+
* @param base Existing window in the splitter.
497+
* @param weight Weight of the new window.
498+
*
499+
* The width of the existing cell will be proportionally split between the
500+
* new and existing windows based on their weight.
501+
*/
502+
void AddLeftOf(wxWindow *window, wxWindow *base, float weight = 1.0f);
503+
504+
/**
505+
* @brief Split an existing cell, inserting a new window to the right.
506+
*
507+
* @param window New window to be added to the splitter.
508+
* @param base Existing window in the splitter.
509+
* @param weight Weight of the new window.
510+
*
511+
* The width of the existing cell will be proportionally split between the
512+
* new and existing windows based on their weight.
513+
*/
514+
void AddRightOf(wxWindow *window, wxWindow *base, float weight = 1.0f);
515+
516+
/**
517+
* @brief Split an existing cell, inserting a new window above.
518+
*
519+
* @param window New window to be added to the splitter.
520+
* @param base Existing window in the splitter.
521+
* @param weight Weight of the new window.
522+
*
523+
* The height of the existing cell will be proportionally split between the
524+
* new and existing windows based on their weight.
525+
*/
526+
void AddAbove(wxWindow *window, wxWindow *base, float weight = 1.0f);
527+
528+
/**
529+
* @brief Split an existing cell, inserting a new window below.
530+
*
531+
* @param window New window to be added to the splitter.
532+
* @param base Existing window in the splitter.
533+
* @param weight Weight of the new window.
534+
*
535+
* The height of the existing cell will be proportionally split between the
536+
* new and existing windows based on their weight.
537+
*/
538+
void AddBelow(wxWindow *window, wxWindow *base, float weight = 1.0f);
492539

493540
/**
494541
* @brief Remove a child window from the splitter without destroying it.

0 commit comments

Comments
 (0)