improve place fit when margin is given

This commit is contained in:
Jinhao 2017-04-29 11:24:35 +08:00
parent 58cb215f7b
commit 0511a300d6
2 changed files with 152 additions and 72 deletions

View File

@ -807,14 +807,9 @@ namespace nana
if((ratio > 0.001) && (fv > 0)) if((ratio > 0.001) && (fv > 0))
fv /= ratio; fv /= ratio;
if (!this->weight.empty()) int set_weight = 0;
{
if(!this->is_percent()) if ((fit_policy::none != this->fit) && this->field)
fv = this->weight.real();
}
else
{
if (fit_policy::none != this->fit)
{ {
std::size_t fit_count = 0; std::size_t fit_count = 0;
@ -822,6 +817,7 @@ namespace nana
auto const fit_horz = (fit_policy::vert == this->fit); auto const fit_horz = (fit_policy::vert == this->fit);
std::size_t pos = 0; std::size_t pos = 0;
for (auto & elm : this->field->elements) for (auto & elm : this->field->elements)
{ {
++pos; ++pos;
@ -847,7 +843,12 @@ namespace nana
floor.first += extent->second.width; floor.first += extent->second.width;
max_value = (std::max)(max_value, (vert_fields ? extent->second.width : extent->second.height)); max_value = (std::max)(max_value, (vert_fields ? extent->second.width : extent->second.height));
if (0 == set_weight)
set_weight = 1;
} }
else
set_weight = -1;
} }
if (max_value) if (max_value)
@ -858,7 +859,7 @@ namespace nana
floor.second = max_value; floor.second = max_value;
} }
//reverse deduction with gap
if (fit_count > 1) if (fit_count > 1)
{ {
double percent = 0; double percent = 0;
@ -878,9 +879,35 @@ namespace nana
fv *= (1 + percent); fv *= (1 + percent);
} }
//reverse deduction with margin
double margin_per = _m_extend_with_margin(0, floor.second);
margin_per += _m_extend_with_margin(2, floor.second);
if (margin_per < 1)
floor.second /= (1 - margin_per);
margin_per = _m_extend_with_margin(1, floor.first);
margin_per += _m_extend_with_margin(3, floor.first);
if (margin_per < 1)
floor.first /= (1 - margin_per);
} }
if (!this->weight.empty())
{
if (!this->is_percent())
{
//Cancel to set weight
if (fv <= this->weight.real())
set_weight = -1;
}
}
if (1 == set_weight)
this->weight.assign(static_cast<int>(fv));
run_.weight_floor = floor; run_.weight_floor = floor;
}
} }
return floor; return floor;
@ -1014,6 +1041,19 @@ namespace nana
return nullptr; return nullptr;
} }
public: public:
double _m_extend_with_margin(std::size_t edge, double & extended)
{
auto margin_edge = margin.get_edge(edge);
if (!margin_edge.empty())
{
if (margin_edge.kind_of() != number_t::kind::percent)
extended += margin_edge.real();
else
return margin_edge.real();
}
return 0;
}
static void _m_visible_for_child(division * div, bool vsb) noexcept static void _m_visible_for_child(division * div, bool vsb) noexcept
{ {
for (auto & child : div->children) for (auto & child : div->children)
@ -1104,7 +1144,9 @@ namespace nana
child_px = npx; child_px = npx;
} }
else else
{
child_px = static_cast<unsigned>(child->weight.integer()); child_px = static_cast<unsigned>(child->weight.integer());
}
//Use 'endpos' to calc width is to avoid deviation //Use 'endpos' to calc width is to avoid deviation
int endpos = static_cast<int>(position + child_px); int endpos = static_cast<int>(position + child_px);
@ -2816,7 +2858,6 @@ namespace nana
if (!weight.empty()) if (!weight.empty())
div->weight = weight; div->weight = weight;
div->gap = std::move(gap); div->gap = std::move(gap);
//attach the field to the division //attach the field to the division

View File

@ -591,6 +591,45 @@ namespace nana
margins_ = v; margins_ = v;
} }
number_t get_edge(std::size_t edge) const
{
int il{ -1 }, ir{ -1 }, it{ -1 }, ib{ -1 }; //index of four corners in margin
switch (margins_.size())
{
case 0: break;
case 1: //top
il = ir = it = ib = 0;
break;
case 2://top,bottom and left,right
it = ib = 0;
il = ir = 1;
break;
default:
il = 3; //left
case 3: //top, right, bottom
it = 0;
ir = 1;
ib = 2;
}
int pos = 0;
switch (edge)
{
case 0: //top
pos = it; break;
case 1: //right
pos = ir; break;
case 2: //bottom
pos = ib; break;
case 3: //left
pos = il; break;
default:
return number_t{};
}
return (-1 == pos ? number_t{} : margins_[pos]);
}
nana::rectangle area(const ::nana::rectangle& field_area) const nana::rectangle area(const ::nana::rectangle& field_area) const
{ {
if (margins_.empty()) if (margins_.empty())
@ -613,7 +652,7 @@ namespace nana
{ {
case 0: break; case 0: break;
case 1: //top case 1: //top
it = 0; il = ir = it = ib = 0;
break; break;
case 2://top,bottom and left,right case 2://top,bottom and left,right
it = ib = 0; it = ib = 0;