OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved. | 2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved. |
3 * | 3 * |
4 * Portions are Copyright (C) 1998 Netscape Communications Corporation. | 4 * Portions are Copyright (C) 1998 Netscape Communications Corporation. |
5 * | 5 * |
6 * Other contributors: | 6 * Other contributors: |
7 * Robert O'Callahan <roc+@cs.cmu.edu> | 7 * Robert O'Callahan <roc+@cs.cmu.edu> |
8 * David Baron <dbaron@fas.harvard.edu> | 8 * David Baron <dbaron@fas.harvard.edu> |
9 * Christian Biesinger <cbiesinger@web.de> | 9 * Christian Biesinger <cbiesinger@web.de> |
10 * Randall Jesup <rjesup@wgate.com> | 10 * Randall Jesup <rjesup@wgate.com> |
(...skipping 421 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
432 return false; | 432 return false; |
433 | 433 |
434 // Otherwise we are paginated by the columns block. | 434 // Otherwise we are paginated by the columns block. |
435 return true; | 435 return true; |
436 } | 436 } |
437 | 437 |
438 // Convert a bounding box from flow thread coordinates, relative to |layer|, to visual coordinates, relative to |ancestorLayer|. | 438 // Convert a bounding box from flow thread coordinates, relative to |layer|, to visual coordinates, relative to |ancestorLayer|. |
439 static void convertFromFlowThreadToVisualBoundingBoxInAncestor(const RenderLayer * layer, const RenderLayer* ancestorLayer, LayoutRect& rect) | 439 static void convertFromFlowThreadToVisualBoundingBoxInAncestor(const RenderLayer * layer, const RenderLayer* ancestorLayer, LayoutRect& rect) |
440 { | 440 { |
441 RenderLayer* paginationLayer = layer->enclosingPaginationLayer(); | 441 RenderLayer* paginationLayer = layer->enclosingPaginationLayer(); |
442 ASSERT(paginationLayer); | 442 if (paginationLayer == layer) { |
443 // If |layer| is the flow thread, we want to convert and translate the r ectangle with | |
444 // respect to the ancestor flow thread (pagination layer), if any. This typically happens | |
445 // when this function is called recursively. | |
446 if (ancestorLayer == paginationLayer) | |
447 return; // But if we've got to the layer where we should stop, do so . | |
448 paginationLayer = layer->parent()->enclosingPaginationLayer(); | |
449 } | |
450 if (!paginationLayer) { | |
451 layer->convertToLayerCoords(ancestorLayer, rect); | |
452 return; | |
453 } | |
443 RenderFlowThread* flowThread = toRenderFlowThread(paginationLayer->renderer( )); | 454 RenderFlowThread* flowThread = toRenderFlowThread(paginationLayer->renderer( )); |
444 | 455 |
445 // First make the flow thread rectangle relative to the flow thread, not to |layer|. | 456 // First make the flow thread rectangle relative to the flow thread, not to |layer|. |
446 LayoutPoint offsetWithinPaginationLayer; | 457 LayoutPoint offsetWithinPaginationLayer; |
447 layer->convertToLayerCoords(paginationLayer, offsetWithinPaginationLayer); | 458 layer->convertToLayerCoords(paginationLayer, offsetWithinPaginationLayer); |
448 rect.moveBy(offsetWithinPaginationLayer); | 459 rect.moveBy(offsetWithinPaginationLayer); |
449 | 460 |
450 // Then make the rectangle visual, relative to the fragmentation context. Sp lit our box up into | 461 // Then make the rectangle visual, relative to the fragmentation context. Sp lit our box up into |
451 // the actual fragment boxes that render in the columns/pages and unite thos e together to get | 462 // the actual fragment boxes that render in the columns/pages and unite thos e together to get |
452 // our true bounding box. | 463 // our true bounding box. |
453 rect = flowThread->fragmentsBoundingBox(rect); | 464 rect = flowThread->fragmentsBoundingBox(rect); |
454 | 465 |
455 // Finally, make the visual rectangle relative to |ancestorLayer|. | 466 // Finally, make the visual rectangle relative to |ancestorLayer|. |
456 // FIXME: Handle nested fragmentation contexts (crbug.com/423076). For now j ust give up if there | 467 if (ancestorLayer->enclosingPaginationLayer() != paginationLayer) { |
chrishtr
2014/12/19 19:42:27
Why do you need the recursion both here and in vis
mstensho (USE GERRIT)
2015/01/06 21:35:10
Ideally, we should break the rectangle into a boun
| |
457 // are different pagination layers involved. | 468 // If we're inside a nested fragmentation context, for each ancestor fra gmentation context |
458 if (!ancestorLayer->enclosingPaginationLayer() || ancestorLayer->enclosingPa ginationLayer() != paginationLayer) { | 469 // we have to examine, we need to do another flow-thread-to-visual trans lation of both the |
459 // The easy case. The ancestor layer is not within the pagination layer. | 470 // offset and the bounding box. If this is the outermost or only fragmen tation context, on |
460 paginationLayer->convertToLayerCoords(ancestorLayer, rect); | 471 // the other hand, we just translate the rectangle to make it relative t o |ancestorLayer|. |
472 convertFromFlowThreadToVisualBoundingBoxInAncestor(paginationLayer, ance storLayer, rect); | |
461 return; | 473 return; |
462 } | 474 } |
463 // The ancestor layer is also inside the pagination layer, so we need to sub tract the visual | 475 // The ancestor layer is inside the same pagination layer as |layer|, so we need to subtract |
464 // distance from the ancestor layer to the pagination layer. | 476 // the visual distance from the ancestor layer to the pagination layer. |
465 rect.moveBy(-ancestorLayer->visualOffsetFromAncestor(paginationLayer)); | 477 rect.moveBy(-ancestorLayer->visualOffsetFromAncestor(paginationLayer)); |
466 } | 478 } |
467 | 479 |
468 bool RenderLayer::useRegionBasedColumns() const | 480 bool RenderLayer::useRegionBasedColumns() const |
469 { | 481 { |
470 return renderer()->document().regionBasedColumnsEnabled(); | 482 return renderer()->document().regionBasedColumnsEnabled(); |
471 } | 483 } |
472 | 484 |
473 void RenderLayer::updatePaginationRecursive(bool needsPaginationUpdate) | 485 void RenderLayer::updatePaginationRecursive(bool needsPaginationUpdate) |
474 { | 486 { |
(...skipping 971 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1446 | 1458 |
1447 void RenderLayer::convertToLayerCoords(const RenderLayer* ancestorLayer, LayoutR ect& rect) const | 1459 void RenderLayer::convertToLayerCoords(const RenderLayer* ancestorLayer, LayoutR ect& rect) const |
1448 { | 1460 { |
1449 LayoutPoint delta; | 1461 LayoutPoint delta; |
1450 convertToLayerCoords(ancestorLayer, delta); | 1462 convertToLayerCoords(ancestorLayer, delta); |
1451 rect.moveBy(delta); | 1463 rect.moveBy(delta); |
1452 } | 1464 } |
1453 | 1465 |
1454 LayoutPoint RenderLayer::visualOffsetFromAncestor(const RenderLayer* ancestorLay er) const | 1466 LayoutPoint RenderLayer::visualOffsetFromAncestor(const RenderLayer* ancestorLay er) const |
1455 { | 1467 { |
1468 LayoutPoint offset; | |
1469 if (ancestorLayer == this) | |
1470 return offset; | |
1456 RenderLayer* paginationLayer = enclosingPaginationLayer(); | 1471 RenderLayer* paginationLayer = enclosingPaginationLayer(); |
1457 LayoutPoint offset; | 1472 if (paginationLayer == this) |
1458 if (!paginationLayer || paginationLayer == this) { | 1473 paginationLayer = parent()->enclosingPaginationLayer(); |
1474 if (!paginationLayer) { | |
1459 convertToLayerCoords(ancestorLayer, offset); | 1475 convertToLayerCoords(ancestorLayer, offset); |
1460 return offset; | 1476 return offset; |
1461 } | 1477 } |
1462 | 1478 |
1463 RenderFlowThread* flowThread = toRenderFlowThread(paginationLayer->renderer( )); | 1479 RenderFlowThread* flowThread = toRenderFlowThread(paginationLayer->renderer( )); |
1464 convertToLayerCoords(paginationLayer, offset); | 1480 convertToLayerCoords(paginationLayer, offset); |
1465 offset = flowThread->flowThreadPointToVisualPoint(offset); | 1481 offset = flowThread->flowThreadPointToVisualPoint(offset); |
1466 if (ancestorLayer == paginationLayer) | 1482 if (ancestorLayer == paginationLayer) |
1467 return offset; | 1483 return offset; |
1468 | 1484 |
1469 // FIXME: Handle nested fragmentation contexts (crbug.com/423076). For now j ust give up if there | 1485 if (ancestorLayer->enclosingPaginationLayer() != paginationLayer) { |
1470 // are different pagination layers involved. | |
1471 if (!ancestorLayer->enclosingPaginationLayer() || ancestorLayer->enclosingPa ginationLayer() != paginationLayer) { | |
1472 // The easy case. The ancestor layer is not within the pagination layer. | |
1473 offset.moveBy(paginationLayer->visualOffsetFromAncestor(ancestorLayer)); | 1486 offset.moveBy(paginationLayer->visualOffsetFromAncestor(ancestorLayer)); |
1474 } else { | 1487 } else { |
1475 // The ancestor layer is also inside the pagination layer, so we need to subtract the visual | 1488 // The ancestor layer is also inside the pagination layer, so we need to subtract the visual |
1476 // distance from the ancestor layer to the pagination layer. | 1489 // distance from the ancestor layer to the pagination layer. |
1477 offset.moveBy(-ancestorLayer->visualOffsetFromAncestor(paginationLayer)) ; | 1490 offset.moveBy(-ancestorLayer->visualOffsetFromAncestor(paginationLayer)) ; |
1478 } | 1491 } |
1479 return offset; | 1492 return offset; |
1480 } | 1493 } |
1481 | 1494 |
1482 void RenderLayer::didUpdateNeedsCompositedScrolling() | 1495 void RenderLayer::didUpdateNeedsCompositedScrolling() |
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1548 ClipRect outlineRectInFlowThread; | 1561 ClipRect outlineRectInFlowThread; |
1549 clipper().calculateRects(paginationClipRectsContext, LayoutRect::infiniteInt Rect(), layerBoundsInFlowThread, backgroundRectInFlowThread, foregroundRectInFlo wThread, | 1562 clipper().calculateRects(paginationClipRectsContext, LayoutRect::infiniteInt Rect(), layerBoundsInFlowThread, backgroundRectInFlowThread, foregroundRectInFlo wThread, |
1550 outlineRectInFlowThread, &offsetWithinPaginatedLayer); | 1563 outlineRectInFlowThread, &offsetWithinPaginatedLayer); |
1551 | 1564 |
1552 // Take our bounding box within the flow thread and clip it. | 1565 // Take our bounding box within the flow thread and clip it. |
1553 LayoutRect layerBoundingBoxInFlowThread = layerBoundingBox ? *layerBoundingB ox : physicalBoundingBox(enclosingPaginationLayer(), &offsetWithinPaginatedLayer ); | 1566 LayoutRect layerBoundingBoxInFlowThread = layerBoundingBox ? *layerBoundingB ox : physicalBoundingBox(enclosingPaginationLayer(), &offsetWithinPaginatedLayer ); |
1554 layerBoundingBoxInFlowThread.intersect(backgroundRectInFlowThread.rect()); | 1567 layerBoundingBoxInFlowThread.intersect(backgroundRectInFlowThread.rect()); |
1555 | 1568 |
1556 // Make the dirty rect relative to the fragmentation context (multicol conta iner, etc.). | 1569 // Make the dirty rect relative to the fragmentation context (multicol conta iner, etc.). |
1557 RenderFlowThread* enclosingFlowThread = toRenderFlowThread(enclosingPaginati onLayer()->renderer()); | 1570 RenderFlowThread* enclosingFlowThread = toRenderFlowThread(enclosingPaginati onLayer()->renderer()); |
1558 LayoutPoint offsetOfPaginationLayerFromRoot; | 1571 LayoutPoint offsetOfPaginationLayerFromRoot; // Visual offset from the root layer to the nearest fragmentation context. |
1559 // FIXME: more work needed if there are nested pagination layers. | 1572 if (rootLayer->enclosingPaginationLayer() == enclosingPaginationLayer()) { |
1560 if (rootLayer != enclosingPaginationLayer() && rootLayer->enclosingPaginatio nLayer() == enclosingPaginationLayer()) { | 1573 // The root layer is in the same fragmentation context as this layer, so we need to look |
1561 // The root layer is inside the fragmentation context. So we need to loo k inside it and find | 1574 // inside it and subtract the offset between the fragmentation context a nd the root layer. |
1562 // the visual offset from the fragmentation context. | 1575 offsetOfPaginationLayerFromRoot = -rootLayer->visualOffsetFromAncestor(e nclosingPaginationLayer()); |
1563 LayoutPoint flowThreadOffset; | |
1564 rootLayer->convertToLayerCoords(enclosingPaginationLayer(), flowThreadOf fset); | |
1565 offsetOfPaginationLayerFromRoot = -enclosingFlowThread->flowThreadPointT oVisualPoint(flowThreadOffset); | |
1566 } else { | 1576 } else { |
1567 enclosingPaginationLayer()->convertToLayerCoords(rootLayer, offsetOfPagi nationLayerFromRoot); | 1577 offsetOfPaginationLayerFromRoot = enclosingPaginationLayer()->visualOffs etFromAncestor(rootLayer); |
1568 } | 1578 } |
1569 LayoutRect dirtyRectInFlowThread(dirtyRect); | 1579 LayoutRect dirtyRectInFlowThread(dirtyRect); |
1570 dirtyRectInFlowThread.moveBy(-offsetOfPaginationLayerFromRoot); | 1580 dirtyRectInFlowThread.moveBy(-offsetOfPaginationLayerFromRoot); |
1571 | 1581 |
1572 // Tell the flow thread to collect the fragments. We pass enough information to create a minimal number of fragments based off the pages/columns | 1582 // Tell the flow thread to collect the fragments. We pass enough information to create a minimal number of fragments based off the pages/columns |
1573 // that intersect the actual dirtyRect as well as the pages/columns that int ersect our layer's bounding box. | 1583 // that intersect the actual dirtyRect as well as the pages/columns that int ersect our layer's bounding box. |
1574 enclosingFlowThread->collectLayerFragments(fragments, layerBoundingBoxInFlow Thread, dirtyRectInFlowThread); | 1584 enclosingFlowThread->collectLayerFragments(fragments, layerBoundingBoxInFlow Thread, dirtyRectInFlowThread); |
1575 | 1585 |
1576 if (fragments.isEmpty()) | 1586 if (fragments.isEmpty()) |
1577 return; | 1587 return; |
(...skipping 1322 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2900 } | 2910 } |
2901 } | 2911 } |
2902 | 2912 |
2903 void showLayerTree(const blink::RenderObject* renderer) | 2913 void showLayerTree(const blink::RenderObject* renderer) |
2904 { | 2914 { |
2905 if (!renderer) | 2915 if (!renderer) |
2906 return; | 2916 return; |
2907 showLayerTree(renderer->enclosingLayer()); | 2917 showLayerTree(renderer->enclosingLayer()); |
2908 } | 2918 } |
2909 #endif | 2919 #endif |
OLD | NEW |