| 1 |
lars |
1 |
<?php
|
|
|
2 |
|
|
|
3 |
require_once(HTML2PS_DIR.'filter.post.positioned.class.php');
|
|
|
4 |
|
|
|
5 |
class LayoutEngineDefault extends LayoutEngine {
|
|
|
6 |
function process(&$box, &$media, &$driver, &$context) {
|
|
|
7 |
// Calculate the size of text boxes
|
|
|
8 |
if (is_null($box->reflow_text($driver))) {
|
|
|
9 |
error_log("LayoutEngineDefault::process: reflow_text call failed");
|
|
|
10 |
return null;
|
|
|
11 |
};
|
|
|
12 |
|
|
|
13 |
// Explicitly remove any height declarations from the BODY-generated box;
|
|
|
14 |
// BODY should always fill last page completely. Percentage height of the BODY is meaningless
|
|
|
15 |
// on the paged media.
|
|
|
16 |
$box->_height_constraint = new HCConstraint(null, null, null);
|
|
|
17 |
|
|
|
18 |
$margin = $box->get_css_property(CSS_MARGIN);
|
|
|
19 |
$margin->calcPercentages(mm2pt($media->width() - $media->margins['left'] - $media->margins['right']));
|
|
|
20 |
$box->setCSSProperty(CSS_MARGIN, $margin);
|
|
|
21 |
|
|
|
22 |
$box->width = mm2pt($media->width() - $media->margins['left'] - $media->margins['right']) -
|
|
|
23 |
$box->_get_hor_extra();
|
|
|
24 |
$box->setCSSProperty(CSS_WIDTH, new WCConstant($box->width));
|
|
|
25 |
|
|
|
26 |
$box->height = mm2pt($media->real_height()) - $box->_get_vert_extra();
|
|
|
27 |
|
|
|
28 |
$box->put_top(mm2pt($media->height() -
|
|
|
29 |
$media->margins['top']) -
|
|
|
30 |
$box->get_extra_top());
|
|
|
31 |
|
|
|
32 |
$box->put_left(mm2pt($media->margins['left']) +
|
|
|
33 |
$box->get_extra_left());
|
|
|
34 |
|
|
|
35 |
|
|
|
36 |
$flag = false;
|
|
|
37 |
$whitespace_flag = false;
|
|
|
38 |
$box->reflow_whitespace($flag, $whitespace_flag);
|
|
|
39 |
|
|
|
40 |
$box->pre_reflow_images();
|
|
|
41 |
|
|
|
42 |
$viewport = new FlowViewport();
|
|
|
43 |
$viewport->left = mm2pt($media->margins['left']);
|
|
|
44 |
$viewport->top = mm2pt($media->height() - $media->margins['top']);
|
|
|
45 |
$viewport->width = mm2pt($media->width() - $media->margins['left'] - $media->margins['right']);
|
|
|
46 |
$viewport->height = mm2pt($media->height() - $media->margins['top'] - $media->margins['bottom']);
|
|
|
47 |
|
|
|
48 |
$fake_parent = null;
|
|
|
49 |
$context->push_viewport($viewport);
|
|
|
50 |
|
|
|
51 |
$box->reflow($fake_parent, $context);
|
|
|
52 |
|
|
|
53 |
// Make the top-level box competely fill the last page
|
|
|
54 |
$page_real_height = mm2pt($media->real_height());
|
|
|
55 |
|
|
|
56 |
// Note we cannot have less than 1 page in our doc; max() call
|
|
|
57 |
// is required as we, in general, CAN have the content height strictly equal to 0.
|
|
|
58 |
// In this case wi still render the very first page
|
|
|
59 |
$pages = max(1,ceil($box->get_full_height() / $page_real_height));
|
|
|
60 |
|
|
|
61 |
/**
|
|
|
62 |
* Set body box height so it will fit the page exactly
|
|
|
63 |
*/
|
|
|
64 |
$box->height = $pages * $page_real_height - $box->_get_vert_extra();
|
|
|
65 |
|
|
|
66 |
$driver->set_expected_pages($pages);
|
|
|
67 |
|
|
|
68 |
/**
|
|
|
69 |
* Flow absolute-positioned boxes;
|
|
|
70 |
* note that we should know the number of expected pages at this moment, unless
|
|
|
71 |
* we will not be able to calculate positions for elements using 'bottom: ...' CSS property
|
|
|
72 |
*/
|
|
|
73 |
for ($i=0, $num_positioned = count($context->absolute_positioned); $i < $num_positioned; $i++) {
|
|
|
74 |
$context->push();
|
|
|
75 |
$context->absolute_positioned[$i]->reflow_absolute($context);
|
|
|
76 |
$context->pop();
|
|
|
77 |
};
|
|
|
78 |
|
|
|
79 |
// Flow fixed-positioned box
|
|
|
80 |
for ($i=0, $num_positioned = count($context->fixed_positioned); $i < $num_positioned; $i++) {
|
|
|
81 |
$context->push();
|
|
|
82 |
$context->fixed_positioned[$i]->reflow_fixed($context);
|
|
|
83 |
$context->pop();
|
|
|
84 |
};
|
|
|
85 |
|
|
|
86 |
$box->reflow_inline();
|
|
|
87 |
|
|
|
88 |
return true;
|
|
|
89 |
}
|
|
|
90 |
}
|
|
|
91 |
?>
|