# Path: weasyprint/layout/absolute.py
# def absolute_layout(context, placeholder, containing_block, fixed_boxes,
#                     bottom_space, skip_stack):
#     """Set the width of absolute positioned ``box``."""
#     assert not placeholder._layout_done
#     box = placeholder._box
#     new_box, resume_at = absolute_box_layout(
#         context, box, containing_block, fixed_boxes, bottom_space, skip_stack)
#     placeholder.set_laid_out_box(new_box)
#     if resume_at:
#         context.broken_out_of_flow.append(
#             (box, containing_block, resume_at))
# 
# Path: weasyprint/layout/percent.py
# def resolve_percentages(box, containing_block, main_flex_direction=None):
#     """Set used values as attributes of the box object."""
#     if isinstance(containing_block, boxes.Box):
#         # cb is short for containing block
#         cb_width = containing_block.width
#         cb_height = containing_block.height
#     else:
#         cb_width, cb_height = containing_block
#     if isinstance(box, boxes.PageBox):
#         maybe_height = cb_height
#     else:
#         maybe_height = cb_width
#     resolve_one_percentage(box, 'margin_left', cb_width)
#     resolve_one_percentage(box, 'margin_right', cb_width)
#     resolve_one_percentage(box, 'margin_top', maybe_height)
#     resolve_one_percentage(box, 'margin_bottom', maybe_height)
#     resolve_one_percentage(box, 'padding_left', cb_width)
#     resolve_one_percentage(box, 'padding_right', cb_width)
#     resolve_one_percentage(box, 'padding_top', maybe_height)
#     resolve_one_percentage(box, 'padding_bottom', maybe_height)
#     resolve_one_percentage(box, 'width', cb_width)
#     resolve_one_percentage(box, 'min_width', cb_width, main_flex_direction)
#     resolve_one_percentage(box, 'max_width', cb_width, main_flex_direction)
# 
#     # XXX later: top, bottom, left and right on positioned elements
# 
#     if cb_height == 'auto':
#         # Special handling when the height of the containing block
#         # depends on its content.
#         height = box.style['height']
#         if height == 'auto' or height.unit == '%':
#             box.height = 'auto'
#         else:
#             assert height.unit == 'px'
#             box.height = height.value
#         resolve_one_percentage(box, 'min_height', 0, main_flex_direction)
#         resolve_one_percentage(box, 'max_height', inf, main_flex_direction)
#     else:
#         resolve_one_percentage(box, 'height', cb_height)
#         resolve_one_percentage(
#             box, 'min_height', cb_height, main_flex_direction)
#         resolve_one_percentage(
#             box, 'max_height', cb_height, main_flex_direction)
# 
#     # Used value == computed value
#     for side in ['top', 'right', 'bottom', 'left']:
#         prop = f'border_{side}_width'
#         setattr(box, prop, box.style[prop])
# 
#     # Shrink *content* widths and heights according to box-sizing
#     # Thanks heavens and the spec: Our validator rejects negative values
#     # for padding and border-width
#     if box.style['box_sizing'] == 'border-box':
#         horizontal_delta = (
#             box.padding_left + box.padding_right +
#             box.border_left_width + box.border_right_width)
#         vertical_delta = (
#             box.padding_top + box.padding_bottom +
#             box.border_top_width + box.border_bottom_width)
#     elif box.style['box_sizing'] == 'padding-box':
#         horizontal_delta = box.padding_left + box.padding_right
#         vertical_delta = box.padding_top + box.padding_bottom
#     else:
#         assert box.style['box_sizing'] == 'content-box'
#         horizontal_delta = 0
#         vertical_delta = 0
# 
#     # Keep at least min_* >= 0 to prevent funny output in case box.width or
#     # box.height become negative.
#     # Restricting max_* seems reasonable, too.
#     if horizontal_delta > 0:
#         if box.width != 'auto':
#             box.width = max(0, box.width - horizontal_delta)
#         box.max_width = max(0, box.max_width - horizontal_delta)
#         if box.min_width != 'auto':
#             box.min_width = max(0, box.min_width - horizontal_delta)
#     if vertical_delta > 0:
#         if box.height != 'auto':
#             box.height = max(0, box.height - vertical_delta)
#         box.max_height = max(0, box.max_height - vertical_delta)
#         if box.min_height != 'auto':
#             box.min_height = max(0, box.min_height - vertical_delta)


from math import floor, inf
from .absolute import absolute_layout
from .percent import resolve_percentages
    from .block import (
        block_box_layout, block_level_layout, block_level_width,
        collapse_margin)
                columns_and_blocks.append(column_children)
            columns_and_blocks.append(child.copy())
            column_children = []
            continue
        column_children.append(child.copy())
    if column_children:
        columns_and_blocks.append(column_children)

    if not box.children:
        next_page = {'break': 'any', 'page': None}
        skip_stack = None

    # Balance.
    #
    # The current algorithm starts from the ideal height (the total height
    # divided by the number of columns). We then iterate until the last column
    # is not the highest one. At the end of each loop, we add the minimal
    # height needed to make one direct child at the top of one column go to the
    # end of the previous column.
    #
    # We rely on a real rendering for each loop, and with a stupid algorithm
    # like this it can last minutes…

    adjoining_margins = []
    current_position_y = box.content_box_y()
    new_children = []
    for column_children_or_block in columns_and_blocks:
        if not isinstance(column_children_or_block, list):
            # We get a spanning block, we display it like other blocks.
            block = column_children_or_block

# Path: weasyprint/layout/absolute.py
# def absolute_layout(context, placeholder, containing_block, fixed_boxes,
#                     bottom_space, skip_stack):
#     """Set the width of absolute positioned ``box``."""
#     assert not placeholder._layout_done
#     box = placeholder._box
#     new_box, resume_at = absolute_box_layout(
#         context, box, containing_block, fixed_boxes, bottom_space, skip_stack)
#     placeholder.set_laid_out_box(new_box)
#     if resume_at:
#         context.broken_out_of_flow.append(
#             (box, containing_block, resume_at))
# 
# Path: weasyprint/layout/percent.py
# def resolve_percentages(box, containing_block, main_flex_direction=None):
#     """Set used values as attributes of the box object."""
#     if isinstance(containing_block, boxes.Box):
#         # cb is short for containing block
#         cb_width = containing_block.width
#         cb_height = containing_block.height
#     else:
#         cb_width, cb_height = containing_block
#     if isinstance(box, boxes.PageBox):
#         maybe_height = cb_height
#     else:
#         maybe_height = cb_width
#     resolve_one_percentage(box, 'margin_left', cb_width)
#     resolve_one_percentage(box, 'margin_right', cb_width)
#     resolve_one_percentage(box, 'margin_top', maybe_height)
#     resolve_one_percentage(box, 'margin_bottom', maybe_height)
#     resolve_one_percentage(box, 'padding_left', cb_width)
#     resolve_one_percentage(box, 'padding_right', cb_width)
#     resolve_one_percentage(box, 'padding_top', maybe_height)
#     resolve_one_percentage(box, 'padding_bottom', maybe_height)
#     resolve_one_percentage(box, 'width', cb_width)
#     resolve_one_percentage(box, 'min_width', cb_width, main_flex_direction)
#     resolve_one_percentage(box, 'max_width', cb_width, main_flex_direction)
# 
#     # XXX later: top, bottom, left and right on positioned elements
# 
#     if cb_height == 'auto':
#         # Special handling when the height of the containing block
#         # depends on its content.
#         height = box.style['height']
#         if height == 'auto' or height.unit == '%':
#             box.height = 'auto'
#         else:
#             assert height.unit == 'px'
#             box.height = height.value
#         resolve_one_percentage(box, 'min_height', 0, main_flex_direction)
#         resolve_one_percentage(box, 'max_height', inf, main_flex_direction)
#     else:
#         resolve_one_percentage(box, 'height', cb_height)
#         resolve_one_percentage(
#             box, 'min_height', cb_height, main_flex_direction)
#         resolve_one_percentage(
#             box, 'max_height', cb_height, main_flex_direction)
# 
#     # Used value == computed value
#     for side in ['top', 'right', 'bottom', 'left']:
#         prop = f'border_{side}_width'
#         setattr(box, prop, box.style[prop])
# 
#     # Shrink *content* widths and heights according to box-sizing
#     # Thanks heavens and the spec: Our validator rejects negative values
#     # for padding and border-width
#     if box.style['box_sizing'] == 'border-box':
#         horizontal_delta = (
#             box.padding_left + box.padding_right +
#             box.border_left_width + box.border_right_width)
#         vertical_delta = (
#             box.padding_top + box.padding_bottom +
#             box.border_top_width + box.border_bottom_width)
#     elif box.style['box_sizing'] == 'padding-box':
#         horizontal_delta = box.padding_left + box.padding_right
#         vertical_delta = box.padding_top + box.padding_bottom
#     else:
#         assert box.style['box_sizing'] == 'content-box'
#         horizontal_delta = 0
#         vertical_delta = 0
# 
#     # Keep at least min_* >= 0 to prevent funny output in case box.width or
#     # box.height become negative.
#     # Restricting max_* seems reasonable, too.
#     if horizontal_delta > 0:
#         if box.width != 'auto':
#             box.width = max(0, box.width - horizontal_delta)
#         box.max_width = max(0, box.max_width - horizontal_delta)
#         if box.min_width != 'auto':
#             box.min_width = max(0, box.min_width - horizontal_delta)
#     if vertical_delta > 0:
#         if box.height != 'auto':
#             box.height = max(0, box.height - vertical_delta)
#         box.max_height = max(0, box.max_height - vertical_delta)
#         if box.min_height != 'auto':
#             box.min_height = max(0, box.min_height - vertical_delta)


# Path: weasyprint/layout/column.py
from math import floor, inf
from .absolute import absolute_layout
from .percent import resolve_percentages
    from .block import (
        block_box_layout, block_level_layout, block_level_width,
        collapse_margin)

                columns_and_blocks.append(column_children)
            columns_and_blocks.append(child.copy())
            column_children = []
            continue
        column_children.append(child.copy())
    if column_children:
        columns_and_blocks.append(column_children)

    if not box.children:
        next_page = {'break': 'any', 'page': None}
        skip_stack = None

    # Balance.
    #
    # The current algorithm starts from the ideal height (the total height
    # divided by the number of columns). We then iterate until the last column
    # is not the highest one. At the end of each loop, we add the minimal
    # height needed to make one direct child at the top of one column go to the
    # end of the previous column.
    #
    # We rely on a real rendering for each loop, and with a stupid algorithm
    # like this it can last minutes…

    adjoining_margins = []
    current_position_y = box.content_box_y()
    new_children = []
    for column_children_or_block in columns_and_blocks:
        if not isinstance(column_children_or_block, list):
            # We get a spanning block, we display it like other blocks.
            block = column_children_or_block

            resolve_percentages(block, containing_block)