mirror of
https://github.com/fltk/fltk.git
synced 2026-03-23 15:35:11 +08:00
Fix Fl_Pack to support more box types.
Old code supported only frame styles, this code can now handle box types with a background.
This commit is contained in:
@@ -21,6 +21,7 @@
|
|||||||
#define Fl_Pack_H
|
#define Fl_Pack_H
|
||||||
|
|
||||||
#include <FL/Fl_Group.H>
|
#include <FL/Fl_Group.H>
|
||||||
|
#include <FL/Fl_Rect.H>
|
||||||
|
|
||||||
/**
|
/**
|
||||||
This widget was designed to add the functionality of compressing and
|
This widget was designed to add the functionality of compressing and
|
||||||
@@ -39,6 +40,12 @@
|
|||||||
resizable() widget is the last widget in the group it is extended to take
|
resizable() widget is the last widget in the group it is extended to take
|
||||||
the full available width or height, respectively, of the Fl_Pack group.
|
the full available width or height, respectively, of the Fl_Pack group.
|
||||||
|
|
||||||
|
\note Fl_Pack is optimized to use a frame-only (`..._FRAME`) box type.
|
||||||
|
Box types with background graphics (`..._BOX`) generally work, but can be
|
||||||
|
slower witch a large number of children. Not all box types work well
|
||||||
|
with FL_Pack. Avoid irregular graphics like FL_DIAMOND_BOX and background
|
||||||
|
images.
|
||||||
|
|
||||||
\note You can nest Fl_Pack widgets or put them inside Fl_Scroll widgets
|
\note You can nest Fl_Pack widgets or put them inside Fl_Scroll widgets
|
||||||
or inside other group widgets but their behavior can sometimes be
|
or inside other group widgets but their behavior can sometimes be
|
||||||
<i>"surprising"</i>. This is partly due to the fact that Fl_Pack widgets
|
<i>"surprising"</i>. This is partly due to the fact that Fl_Pack widgets
|
||||||
@@ -61,6 +68,7 @@ public:
|
|||||||
};
|
};
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
void draw_filler_(const Fl_Rect& rect);
|
||||||
void draw() override;
|
void draw() override;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|||||||
@@ -49,6 +49,22 @@ Fl_Pack::Fl_Pack(int X, int Y, int W, int H, const char *L)
|
|||||||
// type(VERTICAL); // already set like this
|
// type(VERTICAL); // already set like this
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Draw a rectangular area as a background filler.
|
||||||
|
If the box type has a background (is not a frame), this will clip to the
|
||||||
|
rectangular area and draw the box. Otherwise, it will draw a rectangle
|
||||||
|
in widget color.
|
||||||
|
\param[in] rect fill this rectangle inside the widget bounds
|
||||||
|
*/
|
||||||
|
void Fl_Pack::draw_filler_(const Fl_Rect& rect) {
|
||||||
|
if (Fl::box_bg(box())) {
|
||||||
|
fl_push_clip(rect.x(), rect.y(), rect.w(), rect.h());
|
||||||
|
draw_box();
|
||||||
|
fl_pop_clip();
|
||||||
|
} else {
|
||||||
|
fl_rectf(rect.x(), rect.y(), rect.w(), rect.h(), color());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Fl_Pack::draw() {
|
void Fl_Pack::draw() {
|
||||||
int tx = x()+Fl::box_dx(box());
|
int tx = x()+Fl::box_dx(box());
|
||||||
int ty = y()+Fl::box_dy(box());
|
int ty = y()+Fl::box_dy(box());
|
||||||
@@ -102,11 +118,10 @@ void Fl_Pack::draw() {
|
|||||||
}
|
}
|
||||||
if (spacing_ && current_position>maximum_position && box() &&
|
if (spacing_ && current_position>maximum_position && box() &&
|
||||||
(X != o->x() || Y != o->y() || d&FL_DAMAGE_ALL)) {
|
(X != o->x() || Y != o->y() || d&FL_DAMAGE_ALL)) {
|
||||||
fl_color(color());
|
|
||||||
if (horizontal())
|
if (horizontal())
|
||||||
fl_rectf(maximum_position, ty, spacing_, th);
|
draw_filler_( { maximum_position, ty, spacing_, th } );
|
||||||
else
|
else
|
||||||
fl_rectf(tx, maximum_position, tw, spacing_);
|
draw_filler_( { tx, maximum_position, tw, spacing_ } );
|
||||||
}
|
}
|
||||||
if (X != o->x() || Y != o->y() || W != o->w() || H != o->h()) {
|
if (X != o->x() || Y != o->y() || W != o->w() || H != o->h()) {
|
||||||
o->resize(X,Y,W,H);
|
o->resize(X,Y,W,H);
|
||||||
@@ -132,14 +147,12 @@ void Fl_Pack::draw() {
|
|||||||
|
|
||||||
if (horizontal()) {
|
if (horizontal()) {
|
||||||
if (maximum_position < tx+tw && box()) {
|
if (maximum_position < tx+tw && box()) {
|
||||||
fl_color(color());
|
draw_filler_( { maximum_position, ty, tx+tw-maximum_position, th } );
|
||||||
fl_rectf(maximum_position, ty, tx+tw-maximum_position, th);
|
|
||||||
}
|
}
|
||||||
tw = maximum_position-tx;
|
tw = maximum_position-tx;
|
||||||
} else {
|
} else {
|
||||||
if (maximum_position < ty+th && box()) {
|
if (maximum_position < ty+th && box()) {
|
||||||
fl_color(color());
|
draw_filler_( { tx, maximum_position, tw, ty+th-maximum_position } );
|
||||||
fl_rectf(tx, maximum_position, tw, ty+th-maximum_position);
|
|
||||||
}
|
}
|
||||||
th = maximum_position-ty;
|
th = maximum_position-ty;
|
||||||
}
|
}
|
||||||
@@ -153,7 +166,13 @@ void Fl_Pack::draw() {
|
|||||||
d = FL_DAMAGE_ALL;
|
d = FL_DAMAGE_ALL;
|
||||||
}
|
}
|
||||||
if (d&FL_DAMAGE_ALL) {
|
if (d&FL_DAMAGE_ALL) {
|
||||||
draw_box();
|
if (Fl::box_bg(box())) {
|
||||||
|
// Make sure that we only draw the frame part, because the children
|
||||||
|
// and fillers are already rendered at this point.
|
||||||
|
draw_box(fl_frame(box()), x(), y(), w(), h(), color());
|
||||||
|
} else {
|
||||||
|
draw_box();
|
||||||
|
}
|
||||||
draw_label();
|
draw_label();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -186,9 +186,11 @@ Fl_Input::paste_menu_text = gettext("Paste");} {}
|
|||||||
MenuItem {} {
|
MenuItem {} {
|
||||||
label sandals
|
label sandals
|
||||||
callback {[](Fl_Widget*, void*)
|
callback {[](Fl_Widget*, void*)
|
||||||
|
/* If this code generates an error, you are using an older version of Fluid */
|
||||||
|
/* Support for lambda callbacks was added dec 12 2025 */
|
||||||
{
|
{
|
||||||
puts("The shoe is the sign!");
|
puts("The shoe is the sign!");
|
||||||
}} selected
|
}}
|
||||||
xywh {0 0 100 20}
|
xywh {0 0 100 20}
|
||||||
}
|
}
|
||||||
MenuItem {} {
|
MenuItem {} {
|
||||||
@@ -223,6 +225,8 @@ Fl_Input::paste_menu_text = gettext("Paste");} {}
|
|||||||
Fl_Check_Button wShave {
|
Fl_Check_Button wShave {
|
||||||
label shave
|
label shave
|
||||||
callback {[](Fl_Widget* w, void*)->void {
|
callback {[](Fl_Widget* w, void*)->void {
|
||||||
|
/* If this code generates an error, you are using an older version of Fluid */
|
||||||
|
/* Support for lambda callbacks was added dec 12 2025 */
|
||||||
auto* btn = static_cast<Fl_Check_Button*>(w);
|
auto* btn = static_cast<Fl_Check_Button*>(w);
|
||||||
if (btn->value()) {
|
if (btn->value()) {
|
||||||
puts("Shave.");
|
puts("Shave.");
|
||||||
@@ -230,7 +234,7 @@ Fl_Input::paste_menu_text = gettext("Paste");} {}
|
|||||||
puts("Don't shave.");
|
puts("Don't shave.");
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
comment {// Testing lambdas for callbacks}
|
comment {// Testing lambdas for callbacks} selected
|
||||||
xywh {25 212 105 24} down_box DOWN_BOX
|
xywh {25 212 105 24} down_box DOWN_BOX
|
||||||
}
|
}
|
||||||
Fl_Check_Button wBrush {
|
Fl_Check_Button wBrush {
|
||||||
|
|||||||
Reference in New Issue
Block a user