Skip to content

Commit 6e1db84

Browse files
committed
feat: new layout process
1 parent 9f2e349 commit 6e1db84

24 files changed

+1248
-1256
lines changed

lib/css/include/css/computed.h

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,11 @@ LIBCSS_INLINE bool is_css_display_block(const css_computed_style_t *s)
5959
return s->type_bits.display == CSS_DISPLAY_BLOCK;
6060
}
6161

62+
LIBCSS_INLINE bool is_css_border_box_sizing(const css_computed_style_t *s)
63+
{
64+
return s->type_bits.box_sizing == CSS_BOX_SIZING_BORDER_BOX;
65+
}
66+
6267
LIBCSS_INLINE css_numeric_value_t css_padding_x(const css_computed_style_t *s)
6368
{
6469
return s->padding_left + s->padding_right;
@@ -139,6 +144,9 @@ LIBCSS_PUBLIC uint8_t css_computed_left(const css_computed_style_t *s,
139144

140145
LIBCSS_PUBLIC uint8_t css_computed_display(const css_computed_style_t *s);
141146

147+
LIBCSS_PUBLIC uint8_t
148+
css_computed_flex_direction(const css_computed_style_t *s);
149+
142150
LIBCSS_PUBLIC uint8_t
143151
css_computed_vertical_align(const css_computed_style_t *s);
144152

@@ -243,7 +251,7 @@ LIBCSS_PUBLIC void css_compute_absolute_values(
243251
const css_computed_style_t *parent, css_computed_style_t *s,
244252
css_metrics_t *m);
245253

246-
LIBCSS_INLINE css_numeric_value_t css_convert_content_box_width(
254+
LIBCSS_INLINE css_numeric_value_t css_content_box_width_to_width(
247255
css_computed_style_t *s, css_numeric_value_t content_width)
248256
{
249257
if (css_computed_box_sizing(s) == CSS_BOX_SIZING_BORDER_BOX) {
@@ -252,7 +260,7 @@ LIBCSS_INLINE css_numeric_value_t css_convert_content_box_width(
252260
return content_width;
253261
}
254262

255-
LIBCSS_INLINE css_numeric_value_t css_convert_content_box_height(
263+
LIBCSS_INLINE css_numeric_value_t css_content_box_height_to_height(
256264
css_computed_style_t *s, css_numeric_value_t content_height)
257265
{
258266
if (css_computed_box_sizing(s) == CSS_BOX_SIZING_BORDER_BOX) {
@@ -261,7 +269,7 @@ LIBCSS_INLINE css_numeric_value_t css_convert_content_box_height(
261269
return content_height;
262270
}
263271

264-
LIBCSS_INLINE css_numeric_value_t css_convert_border_box_width(
272+
LIBCSS_INLINE css_numeric_value_t css_border_box_width_to_width(
265273
css_computed_style_t *s, css_numeric_value_t border_width)
266274
{
267275
if (css_computed_box_sizing(s) == CSS_BOX_SIZING_CONTENT_BOX) {
@@ -270,7 +278,7 @@ LIBCSS_INLINE css_numeric_value_t css_convert_border_box_width(
270278
return border_width;
271279
}
272280

273-
LIBCSS_INLINE css_numeric_value_t css_convert_border_box_height(
281+
LIBCSS_INLINE css_numeric_value_t css_border_box_height_to_height(
274282
css_computed_style_t *s, css_numeric_value_t border_height)
275283
{
276284
if (css_computed_box_sizing(s) == CSS_BOX_SIZING_CONTENT_BOX) {
@@ -279,6 +287,22 @@ LIBCSS_INLINE css_numeric_value_t css_convert_border_box_height(
279287
return border_height;
280288
}
281289

290+
LIBCSS_INLINE css_numeric_value_t css_width_to_content_box_width(
291+
const css_computed_style_t *s, css_numeric_value_t width)
292+
{
293+
return css_computed_box_sizing(s) == CSS_BOX_SIZING_CONTENT_BOX
294+
? width
295+
: width - css_padding_x(s) - css_border_x(s);
296+
}
297+
298+
LIBCSS_INLINE css_numeric_value_t css_height_to_content_box_height(
299+
const css_computed_style_t *s, css_numeric_value_t height)
300+
{
301+
return css_computed_box_sizing(s) == CSS_BOX_SIZING_CONTENT_BOX
302+
? height
303+
: height - css_padding_y(s) - css_border_y(s);
304+
}
305+
282306
LIBCSS_END_DECLS
283307

284308
#endif

lib/css/src/computed.c

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -398,6 +398,11 @@ uint8_t css_computed_display(const css_computed_style_t *s)
398398
return s->type_bits.display;
399399
}
400400

401+
uint8_t css_computed_flex_direction(const css_computed_style_t *s)
402+
{
403+
return s->type_bits.flex_direction;
404+
}
405+
401406
uint8_t css_computed_vertical_align(const css_computed_style_t *s)
402407
{
403408
return s->type_bits.vertical_align;
@@ -1079,9 +1084,9 @@ static void compute_absolute_width(const css_computed_style_t *parent,
10791084
s->type_bits.width = CSS_WIDTH_FIT_CONTENT;
10801085
break;
10811086
}
1082-
// 当父元素是块级元素且 display 为 block 时,width 为父元素的
1083-
// content box 的宽度
1084-
if (is_css_display_block(parent) &&
1087+
// 当父元素是块级元素时,width 为父元素的 content box 的宽度
1088+
if ((parent->type_bits.display == CSS_DISPLAY_BLOCK ||
1089+
parent->type_bits.display == CSS_DISPLAY_INLINE_BLOCK) &&
10851090
compute_content_box_fixed_width(parent, &parent_value)) {
10861091
value = parent_value - s->margin_left - s->margin_right;
10871092
if (s->type_bits.box_sizing ==

lib/ui-widgets/src/canvas.c

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -63,8 +63,7 @@ static void ui_canvas_on_destroy(ui_widget_t *w)
6363
pd_canvas_destroy(&canvas->buffer);
6464
}
6565

66-
static void ui_canvas_on_auto_size(ui_widget_t *w, float *width, float *height,
67-
ui_layout_rule_t rule)
66+
static void ui_canvas_on_autosize(ui_widget_t *w, float *width, float *height)
6867
{
6968
*width = UI_CANVAS_DEFAULT_WIDTH;
7069
*height = UI_CANVAS_DEFAULT_HEIGHT;
@@ -158,6 +157,6 @@ void ui_register_canvas(void)
158157
ui_canvas.proto->init = ui_canvas_on_init;
159158
ui_canvas.proto->destroy = ui_canvas_on_destroy;
160159
ui_canvas.proto->paint = ui_canvas_on_paint;
161-
ui_canvas.proto->autosize = ui_canvas_on_auto_size;
160+
ui_canvas.proto->autosize = ui_canvas_on_autosize;
162161
ui_canvas.proto->resize = ui_canvas_on_resize;
163162
}

lib/ui-widgets/src/text.c

Lines changed: 17 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -177,35 +177,22 @@ static void ui_text_on_destroy(ui_widget_t *w)
177177
}
178178
}
179179

180-
static void ui_text_on_autosize(ui_widget_t *w, float *width, float *height,
181-
ui_layout_rule_t rule)
180+
static void ui_text_on_autosize(ui_widget_t *w, float *width, float *height)
182181
{
183-
float max_width, max_height;
182+
float max_width = 0, max_height = 0;
184183
ui_text_t *txt = ui_widget_get_data(w, ui_text.prototype);
184+
css_computed_style_t *s = &w->computed_style;
185185
list_t rects;
186186

187-
if (w->parent &&
188-
IS_CSS_FIXED_LENGTH(&w->parent->computed_style, width)) {
189-
max_width = w->parent->content_box.width -
190-
(w->border_box.width - w->content_box.width);
191-
} else {
192-
max_width = 0;
187+
if (IS_CSS_FIXED_LENGTH(s, width)) {
188+
max_width = css_width_to_content_box_width(s, s->width);
189+
} else if (ui_widget_get_max_width(w, &max_width)) {
190+
max_width = css_width_to_content_box_width(s, max_width);
193191
}
194-
switch (rule) {
195-
case UI_LAYOUT_RULE_FIXED_WIDTH:
196-
max_width = w->content_box.width;
197-
max_height = 0;
198-
break;
199-
case UI_LAYOUT_RULE_FIXED_HEIGHT:
200-
max_height = w->content_box.height;
201-
break;
202-
case UI_LAYOUT_RULE_FIXED:
203-
max_width = w->content_box.width;
204-
max_height = w->content_box.height;
205-
break;
206-
default:
207-
max_height = 0;
208-
break;
192+
if (IS_CSS_FIXED_LENGTH(s, height)) {
193+
max_height = css_height_to_content_box_height(s, s->height);
194+
} else if (ui_widget_get_max_height(w, &max_height)) {
195+
max_height = css_height_to_content_box_height(s, max_height);
209196
}
210197
list_create(&rects);
211198
pd_text_set_fixed_size(txt->layer, 0, 0);
@@ -214,6 +201,9 @@ static void ui_text_on_autosize(ui_widget_t *w, float *width, float *height,
214201
pd_text_update(txt->layer, &rects);
215202
*width = pd_text_get_width(txt->layer) / ui_get_actual_scale();
216203
*height = pd_text_get_height(txt->layer) / ui_get_actual_scale();
204+
if (ui_widget_has_class(w, "file-path-field-value")) {
205+
logger_debug("[ui-text] on autosize: (%g, %g)\n", *width, *height);
206+
}
217207
pd_rects_clear(&rects);
218208
}
219209

@@ -229,6 +219,9 @@ static void ui_text_on_resize(ui_widget_t *w, float width, float height)
229219
list_t rects;
230220
list_node_t *node;
231221

222+
if (ui_widget_has_class(w, "file-path-field-value")) {
223+
logger_debug("[ui-text] on resize: (%g, %g)\n", width, height);
224+
}
232225
list_create(&rects);
233226
pd_text_set_fixed_size(txt->layer, fixed_width, fixed_height);
234227
pd_text_set_max_size(txt->layer, fixed_width, fixed_height);

lib/ui-widgets/src/textinput.c

Lines changed: 14 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
/*
2-
* lib/ui-widgets/src/textinput.c: -- textinput widget, used to allow user edit text.
2+
* lib/ui-widgets/src/textinput.c: -- textinput widget, used to allow user edit
3+
* text.
34
*
45
* Copyright (c) 2018-2024, Liu chao <[email protected]> All rights reserved.
56
*
@@ -26,7 +27,7 @@
2627

2728
enum task_type_t { TASK_SET_TEXT, TASK_UPDATE, TASK_TOTAL };
2829

29-
typedef struct ui_textinput_t {
30+
typedef struct ui_textinput {
3031
ui_text_style_t style; /**< 字体样式 */
3132
pd_text_t *layer_source; /**< 实际文本层 */
3233
pd_text_t *layer_mask; /**< 屏蔽后的文本层 */
@@ -371,8 +372,7 @@ static void ui_textinput_update_text(ui_widget_t *widget)
371372
for (list_each(node, &blocks)) {
372373
textinput_process_textblock(widget, node->data);
373374
}
374-
list_destroy(&blocks,
375-
(list_item_destructor_t)textblock_destroy);
375+
list_destroy(&blocks, (list_item_destructor_t)textblock_destroy);
376376
ui_event_init(&ev, "change");
377377
ui_widget_emit_event(widget, ev, NULL);
378378
}
@@ -400,48 +400,21 @@ static void ui_textinput_on_resize(ui_widget_t *w, float width, float height)
400400
pd_rects_clear(&rects);
401401
}
402402

403-
static void ui_textinput_on_auto_size(ui_widget_t *w, float *width,
404-
float *height, ui_layout_rule_t rule)
403+
static void ui_textinput_on_autosize(ui_widget_t *w, float *width,
404+
float *height)
405405
{
406-
int i, n;
406+
int i;
407407
int max_width = 0, max_height = 0;
408408
float scale = ui_get_actual_scale();
409-
410409
ui_textinput_t *edit = ui_widget_get_data(w, ui_textinput_proto);
411410

412-
switch (rule) {
413-
case UI_LAYOUT_RULE_FIXED_WIDTH:
414-
max_width = ui_compute(w->content_box.width);
415-
if (edit->is_multiline_mode) {
416-
n = y_max(pd_text_get_lines_length(edit->layer), 6);
417-
for (max_height = 0, i = 0; i < n; ++i) {
418-
max_height +=
419-
pd_text_get_line_height(edit->layer, i);
420-
}
421-
} else {
422-
max_height = pd_text_get_height(edit->layer);
411+
max_width = ui_compute(DEFAULT_WIDTH);
412+
if (edit->is_multiline_mode) {
413+
for (max_height = 0, i = 0; i < 6; ++i) {
414+
max_height += pd_text_get_line_height(edit->layer, i);
423415
}
424-
break;
425-
case UI_LAYOUT_RULE_FIXED_HEIGHT:
426-
max_width = ui_compute(DEFAULT_WIDTH);
427-
max_height = ui_compute(w->content_box.height);
428-
break;
429-
case UI_LAYOUT_RULE_FIXED:
430-
max_width = ui_compute(w->content_box.width);
431-
max_height = ui_compute(w->content_box.height);
432-
break;
433-
default:
434-
max_width = ui_compute(DEFAULT_WIDTH);
435-
if (edit->is_multiline_mode) {
436-
n = y_max(pd_text_get_lines_length(edit->layer), 6);
437-
for (max_height = 0, i = 0; i < n; ++i) {
438-
max_height +=
439-
pd_text_get_line_height(edit->layer, i);
440-
}
441-
} else {
442-
max_height = pd_text_get_height(edit->layer);
443-
}
444-
break;
416+
} else {
417+
max_height = pd_text_get_height(edit->layer);
445418
}
446419
*height = max_height / scale;
447420
*width = max_width / scale;
@@ -1004,7 +977,7 @@ void ui_register_textinput(void)
1004977
ui_textinput_proto->destroy = ui_textinput_on_destroy;
1005978
ui_textinput_proto->settext = ui_textinput_on_parse_text;
1006979
ui_textinput_proto->setattr = ui_textinput_on_set_attr;
1007-
ui_textinput_proto->autosize = ui_textinput_on_auto_size;
980+
ui_textinput_proto->autosize = ui_textinput_on_autosize;
1008981
ui_textinput_proto->resize = ui_textinput_on_resize;
1009982
ui_textinput_proto->update = ui_textinput_on_update;
1010983
ui_load_css_string(ui_textinput_css, __FILE__);

lib/ui/include/ui/base.h

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,11 @@ LIBUI_PUBLIC ui_widget_t *ui_widget_get_closest(ui_widget_t *w,
105105
const char *type);
106106
LIBUI_PUBLIC dict_t *ui_widget_collect_references(ui_widget_t *w);
107107

108+
LIBUI_PUBLIC float ui_widget_fix_width(ui_widget_t *w, float width);
109+
LIBUI_PUBLIC float ui_widget_fix_height(ui_widget_t *w, float height);
110+
LIBUI_PUBLIC bool ui_widget_get_max_width(ui_widget_t *w, float *width);
111+
LIBUI_PUBLIC bool ui_widget_get_max_height(ui_widget_t *w, float *height);
112+
108113
// Layout
109114

110115
/**
@@ -137,11 +142,7 @@ LIBUI_PUBLIC void ui_widget_set_rules(ui_widget_t *w,
137142
LIBUI_PUBLIC void ui_widget_request_refresh_children(ui_widget_t *widget);
138143
LIBUI_PUBLIC void ui_widget_request_update(ui_widget_t *w);
139144

140-
LIBUI_INLINE void ui_widget_request_reflow(ui_widget_t *w)
141-
{
142-
w->update.should_reflow = true;
143-
ui_widget_request_update(w);
144-
}
145+
LIBUI_PUBLIC void ui_widget_request_reflow(ui_widget_t *w);
145146

146147
LIBUI_INLINE void ui_widget_request_refresh_style(ui_widget_t *w)
147148
{

lib/ui/include/ui/types.h

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -191,7 +191,7 @@ struct ui_widget_prototype_t {
191191
void (*update)(ui_widget_t *, ui_task_type_t);
192192
void (*setattr)(ui_widget_t *, const char *, const char *);
193193
void (*settext)(ui_widget_t *, const char *);
194-
void (*autosize)(ui_widget_t *, float *, float *, ui_layout_rule_t);
194+
void (*autosize)(ui_widget_t *, float *, float *);
195195
void (*resize)(ui_widget_t *, float, float);
196196
void (*paint)(ui_widget_t *, pd_context_t *,
197197
ui_widget_actual_style_t *);
@@ -355,12 +355,6 @@ struct ui_widget_t {
355355
bool disabled;
356356
bool event_blocked;
357357

358-
/**
359-
* Coordinates calculated by the layout system
360-
* The position of the rectangular boxes is calculated based on it
361-
*/
362-
float layout_x, layout_y;
363-
364358
/**
365359
* A box’s “ideal” size in a given axis when given infinite available
366360
* space. See more: https://drafts.csswg.org/css-sizing-3/#max-content

0 commit comments

Comments
 (0)