FTXUI 6.1.9 C++ functional terminal UI.

Loading...
Searching...
No Matches
box_helper.cpp
Go to the documentation of this file.
1// Copyright 2021 Arthur Sonzogni. All rights reserved.
2// Use of this source code is governed by the MIT license that can be found in
3// the LICENSE file.
4#include "ftxui/dom/box_helper.hpp"
5
6#include <algorithm> // for max
7#include <vector> // for vector
8
9 namespace ftxui::box_helper {
10
11 namespace {
12// Called when the size allowed is greater than the requested size. This
13// distributes the extra spaces toward the flexible elements, in relative
14// proportions.
15 void ComputeGrow(std::vector<Element>* elements,
16 int extra_space,
17 int flex_grow_sum) {
18 for (Element& element : *elements) {
19 const int added_space =
20 extra_space * element.flex_grow / std::max(flex_grow_sum, 1);
21 extra_space -= added_space;
22 flex_grow_sum -= element.flex_grow;
23 element.size = element.min_size + added_space;
24 }
25}
26
27// Called when the size allowed is lower than the requested size, and the
28// shrinkable element can absorbe the (negative) extra_space. This distribute
29// the extra_space toward those.
30 void ComputeShrinkEasy(std::vector<Element>* elements,
31 int extra_space,
32 int flex_shrink_sum) {
33 for (Element& element : *elements) {
34 const int added_space = extra_space * element.min_size *
35 element.flex_shrink / std::max(flex_shrink_sum, 1);
36 extra_space -= added_space;
37 flex_shrink_sum -= element.flex_shrink * element.min_size;
38 element.size = element.min_size + added_space;
39 }
40}
41
42// Called when the size allowed is lower than the requested size, and the
43// shrinkable element can not absorbe the (negative) extra_space. This assign
44// zero to shrinkable elements and distribute the remaining (negative)
45// extra_space toward the other non shrinkable elements.
46 void ComputeShrinkHard(std::vector<Element>* elements,
47 int extra_space,
48 int size) {
49 for (Element& element : *elements) {
50 if (element.flex_shrink != 0) {
51 element.size = 0;
52 continue;
53 }
54
55 const int added_space = extra_space * element.min_size / std::max(1, size);
56 extra_space -= added_space;
57 size -= element.min_size;
58
59 element.size = element.min_size + added_space;
60 }
61}
62
63} // namespace
64
65 void Compute(std::vector<Element>* elements, int target_size) {
66 int size = 0;
67 int flex_grow_sum = 0;
68 int flex_shrink_sum = 0;
69 int flex_shrink_size = 0;
70
71 for (auto& element : *elements) {
72 flex_grow_sum += element.flex_grow;
73 flex_shrink_sum += element.min_size * element.flex_shrink;
74 if (element.flex_shrink != 0) {
75 flex_shrink_size += element.min_size;
76 }
77 size += element.min_size;
78 }
79
80 const int extra_space = target_size - size;
81 if (extra_space >= 0) {
82 ComputeGrow(elements, extra_space, flex_grow_sum);
83 } else if (flex_shrink_size + extra_space >= 0) {
84 ComputeShrinkEasy(elements, extra_space, flex_shrink_sum);
85
86 } else {
87 ComputeShrinkHard(elements, extra_space + flex_shrink_size,
88 size - flex_shrink_size);
89 }
90}
91
92} // namespace ftxui::box_helper
box_helper.hpp
ftxui::size
Decorator size(WidthOrHeight, Constraint, int value)
Apply a constraint on the size of an element.
Definition src/ftxui/dom/size.cpp:89
ftxui::box_helper
Definition box_helper.cpp:9
ftxui::box_helper::Compute
void Compute(std::vector< Element > *elements, int target_size)
Definition box_helper.cpp:65
ftxui::box_helper::Element
Definition box_helper.hpp:12