An SVG with no intrinsic size does not draw correct slices when used as a border...
authorcommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Wed, 27 May 2015 04:18:04 +0000 (04:18 +0000)
committercommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Wed, 27 May 2015 04:18:04 +0000 (04:18 +0000)
https://bugs.webkit.org/show_bug.cgi?id=139405

Patch by Said Abou-Hallawa <sabouhallawa@apple.com> on 2015-05-26
Reviewed by Darin Adler.
LayoutTests/imported/mozilla:

* svg/as-image/border-image-simple-2.html: Add "border: 0px none;" to
style of the <div> although the style has "border-image: url() 0 fill;".
If the border width is not set to zero in the style, the <div> will have
a 3px border. This seems to be a bug in WebKit but should be unrelated to
the non-intrinsic-sized images with border-image.

Source/WebCore:

When using a non-intrinsic-sized image as an image-border, all the source
slices have to be extracted from the top-left corner of the source image.
This is because the right and bottom sides of the image can not be known.
Also all the slices should not be stretched. In other words, the sizes of
source slices for a non-intrinsic-sized image should be equal to the sizes
of the destination container slices.

This is not compliant with the css3 w3c specs. I think the specs makes it
harder to predict what exactly will be drawn for the image-border in this
case. See http://www.w3.org/TR/css3-background/#border-image-slice. This
approach is implemented by FireFox. And I think it gives a more predictable
rendering for image-border in the case of non-intrinsic-sized images.

Test: fast/borders/border-image-fill-no-intrinsic-size.html

* CMakeLists.txt:
* WebCore.vcxproj/WebCore.vcxproj:
* WebCore.vcxproj/WebCore.vcxproj.filters:
* WebCore.xcodeproj/project.pbxproj:
* platform/LengthBox.cpp: Removed.
* platform/graphics/LayoutBoxExtent.cpp: Removed.
* platform/graphics/LayoutBoxExtent.h: Removed.
* platform/graphics/LayoutRect.h:
Delete LengthBox.cpp and move all the functionalities to LengthBox.h.
Delete LayoutBoxExtent.cpp since it is the same class as LengthBox.

* css/CSSProperty.cpp:
* platform/text/WritingMode.h:
Move the enums LogicalBoxSide and PhysicalBoxSide
from CSSProperty.cpp to WritingMode.h so it can be used by other classes.

* css/CSSToStyleMap.cpp:
(WebCore::CSSToStyleMap::mapNinePieceImageSlice):
(WebCore::CSSToStyleMap::mapNinePieceImageQuad):
* css/CSSToStyleMap.h:
* inspector/InspectorOverlay.cpp:
(WebCore::buildRendererHighlight):
* rendering/InlineFlowBox.cpp:
(WebCore::InlineFlowBox::addBorderOutsetVisualOverflow):
* rendering/RenderBox.h:
(WebCore::RenderBox::marginLogicalLeft):
(WebCore::RenderBox::marginLogicalRight):
(WebCore::RenderBox::setMarginBefore):
(WebCore::RenderBox::setMarginAfter):
(WebCore::RenderBox::setMarginStart):
(WebCore::RenderBox::setMarginEnd):
* rendering/style/RenderStyle.cpp:
(WebCore::RenderStyle::setClip):
(WebCore::RenderStyle::noneDashboardRegions):
* rendering/style/RenderStyle.h:
Use the new BoxExtent access methods for getting and settings the sides of
LengthBox and LayoutBoxExtent.

* platform/LengthBox.h:
(WebCore::BoxExtent::BoxExtent):
(WebCore::BoxExtent::at):
(WebCore::BoxExtent::top):
(WebCore::BoxExtent::right):
(WebCore::BoxExtent::bottom):
(WebCore::BoxExtent::left):
(WebCore::BoxExtent::setAt):
(WebCore::BoxExtent::setTop):
(WebCore::BoxExtent::setRight):
(WebCore::BoxExtent::setBottom):
(WebCore::BoxExtent::setLeft):
(WebCore::BoxExtent::before):
(WebCore::BoxExtent::end):
(WebCore::BoxExtent::after):
(WebCore::BoxExtent::start):
(WebCore::BoxExtent::setBefore):
(WebCore::BoxExtent::setEnd):
(WebCore::BoxExtent::setAfter):
(WebCore::BoxExtent::setStart):
(WebCore::BoxExtent::operator==):
(WebCore::BoxExtent::operator!=):
(WebCore::LengthBox::LengthBox):
(WebCore::LengthBox::isZero):
(WebCore::LengthBox::left): Deleted.
(WebCore::LengthBox::right): Deleted.
(WebCore::LengthBox::top): Deleted.
(WebCore::LengthBox::bottom): Deleted.
(WebCore::LengthBox::operator==): Deleted.
(WebCore::LengthBox::operator!=): Deleted.
(WebCore::LengthBox::nonZero): Deleted.
Define a new template class for 'BoxExtent'. A 'BoxExtent' represents the
extent of four sides of a box. Use this class template to define the exiting
classes 'LengthBox' and 'LayoutBoxExtent'. Use it also to and define the
new class FloatBoxExtent

* rendering/RenderBoxModelObject.cpp:
(WebCore::RenderBoxModelObject::calculateImageIntrinsicDimensions):
* rendering/RenderBoxModelObject.h:
(WebCore::RenderBoxModelObject::calculateFillTileSize):
* rendering/RenderListMarker.cpp:
(WebCore::RenderListMarker::updateContent):
* rendering/shapes/ShapeOutsideInfo.cpp:
(WebCore::ShapeOutsideInfo::createShapeForImage):
Change the return value of calculateImageIntrinsicDimensions() to be a
bool which indicates whether the image has an intrinsic size or not. Add
a new reference argument to this function receive the resolved image size.

(WebCore::RenderBoxModelObject::paintNinePieceImage): Move all the painting
code of this function to NinePieceImage::paint()

(WebCore::computeBorderImageSide): Deleted.
Renamed to be NinePieceImage::computeSlice().

* rendering/style/BorderData.h:
(WebCore::BorderData::borderWidth): Add a new method to return the extents
of the border in a FloatBoxExtent.

* rendering/style/NinePieceImage.cpp:
(WebCore::NinePieceImage::computeSlice): Moved from NinePieceImage::computeSlice().

(WebCore::NinePieceImage::computeSlices): The first version of this function
computes the slices given their lengths. The slices have to be clamped to
the container size. The second version of this function computes the slices
given their lengths, their actual extents and their source slices.

(WebCore::NinePieceImage::scaleSlicesIfNeeded):  Reduce the slices if they
are too large.

(WebCore::NinePieceImage::isEmptyPieceRect): Returns true if an ImagePiece
should not be drawn.

(WebCore::NinePieceImage::horizontalTileRules):
(WebCore::NinePieceImage::verticalTileRules):
Fill vectors of tiling rules to be passed to GraphicsContext::drawTiledImage()

(WebCore::NinePieceImage::computeIntrinsicRects): Computes the nine pieces
rectangles for an intrinsic-sized container.

(WebCore::NinePieceImage::computeNonIntrinsicRects): Computes the nine
pieces rectangles for an non-intrinsic-sized source image. The computed
rectangles have to start at (0, 0) and their sizes should be equal to
the sizes of the nine pieces rectangles of the destination container.

(WebCore::NinePieceImage::computeIntrinsicSideTileScale):
(WebCore::NinePieceImage::computeIntrinsicMiddleTileScale):
(WebCore::NinePieceImage::computeIntrinsicTileScales):
(WebCore::NinePieceImage::computeNonIntrinsicTileScales):
Computes the scaling factors for drawing the tiles. For non-intrinsic source
images, there should not be any scaling factors.

(WebCore::NinePieceImage::paint): Moved from RenderBoxModelObject::paintNinePieceImage()
but simplified and restructured.

(WebCore::NinePieceImageData::NinePieceImageData): Use nullptr instead of 0.

* rendering/style/NinePieceImage.h:
(WebCore::operator++):
(WebCore::isCornerPiece):
(WebCore::isMiddlePiece):
(WebCore::imagePieceHorizontalSide):
(WebCore::imagePieceVerticalSide):
Add helper functions for the enum ImagePiece.

LayoutTests:

* fast/borders/border-image-fill-no-intrinsic-size-expected.html: Added.
* fast/borders/border-image-fill-no-intrinsic-size.html: Added.
* fast/borders/resources/svg-border-100x100-intrinsic.svg: Added.
* fast/borders/resources/svg-border-140x140-intrinsic.svg: Added.
* fast/borders/resources/svg-border-no-intrinsic.svg: Added.
Make sure the slices of the border-image are drawn correctly. When using an
image with no intrinsic size, all the slices has to be gotten from (0, 0)
of the source image.

* TestExpectations: Removed previously-failing test.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@184895 268f45cc-cd09-0410-ab3c-d52691b4dbfc

35 files changed:
LayoutTests/ChangeLog
LayoutTests/TestExpectations
LayoutTests/fast/borders/border-image-fill-no-intrinsic-size-expected.html [new file with mode: 0644]
LayoutTests/fast/borders/border-image-fill-no-intrinsic-size.html [new file with mode: 0644]
LayoutTests/fast/borders/resources/svg-border-100x100-intrinsic.svg [new file with mode: 0644]
LayoutTests/fast/borders/resources/svg-border-140x140-intrinsic.svg [new file with mode: 0644]
LayoutTests/fast/borders/resources/svg-border-no-intrinsic.svg [new file with mode: 0644]
LayoutTests/imported/mozilla/ChangeLog
LayoutTests/imported/mozilla/svg/as-image/border-image-simple-2.html
Source/WebCore/CMakeLists.txt
Source/WebCore/ChangeLog
Source/WebCore/WebCore.vcxproj/WebCore.vcxproj
Source/WebCore/WebCore.vcxproj/WebCore.vcxproj.filters
Source/WebCore/WebCore.xcodeproj/project.pbxproj
Source/WebCore/css/CSSProperty.cpp
Source/WebCore/css/CSSToStyleMap.cpp
Source/WebCore/css/CSSToStyleMap.h
Source/WebCore/inspector/InspectorOverlay.cpp
Source/WebCore/platform/LengthBox.cpp [deleted file]
Source/WebCore/platform/LengthBox.h
Source/WebCore/platform/graphics/LayoutBoxExtent.cpp [deleted file]
Source/WebCore/platform/graphics/LayoutBoxExtent.h [deleted file]
Source/WebCore/platform/graphics/LayoutRect.h
Source/WebCore/platform/text/WritingMode.h
Source/WebCore/rendering/InlineFlowBox.cpp
Source/WebCore/rendering/RenderBox.h
Source/WebCore/rendering/RenderBoxModelObject.cpp
Source/WebCore/rendering/RenderBoxModelObject.h
Source/WebCore/rendering/RenderListMarker.cpp
Source/WebCore/rendering/shapes/ShapeOutsideInfo.cpp
Source/WebCore/rendering/style/BorderData.h
Source/WebCore/rendering/style/NinePieceImage.cpp
Source/WebCore/rendering/style/NinePieceImage.h
Source/WebCore/rendering/style/RenderStyle.cpp
Source/WebCore/rendering/style/RenderStyle.h

index 43d25ed08d66d34749fcf330b84a953347156d94..e9611a2108f326c6b47c56b40fbc08465a1bd0ef 100644 (file)
@@ -1,3 +1,21 @@
+2015-05-26  Said Abou-Hallawa  <sabouhallawa@apple.com>
+
+        An SVG with no intrinsic size does not draw correct slices when used as a border-image for an HTML element.
+        https://bugs.webkit.org/show_bug.cgi?id=139405
+
+        Reviewed by Darin Adler.
+
+        * fast/borders/border-image-fill-no-intrinsic-size-expected.html: Added.
+        * fast/borders/border-image-fill-no-intrinsic-size.html: Added.
+        * fast/borders/resources/svg-border-100x100-intrinsic.svg: Added.
+        * fast/borders/resources/svg-border-140x140-intrinsic.svg: Added.
+        * fast/borders/resources/svg-border-no-intrinsic.svg: Added.
+        Make sure the slices of the border-image are drawn correctly. When using an
+        image with no intrinsic size, all the slices has to be gotten from (0, 0)
+        of the source image.
+        
+        * TestExpectations: Removed previously-failing test.
+
 2015-05-26  Andreas Kling  <akling@apple.com>
 
         <font face> doesn't support plus character in font family names.
index 7bbca9f4f0110fb610bb8971408da28445f9ec67..fc6800133ac68260490c8df26d62906fe1eee7b8 100644 (file)
@@ -433,7 +433,6 @@ webkit.org/b/139266 imported/mozilla/svg/text/dynamic-multiple-x.svg [ ImageOnly
 webkit.org/b/139282 imported/mozilla/svg/image/image-filter-01.svg [ ImageOnlyFailure ]
 webkit.org/b/139322 imported/mozilla/svg/text/dynamic-non-scaling-stroke.svg [ ImageOnlyFailure ]
 webkit.org/b/139407 imported/mozilla/svg/as-image/border-image-simple-1.html [ ImageOnlyFailure ]
-webkit.org/b/139405 imported/mozilla/svg/as-image/border-image-simple-2.html [ ImageOnlyFailure ]
 webkit.org/b/139412 imported/mozilla/svg/filters/svg-filter-chains/clip-input.svg [ ImageOnlyFailure ]
 webkit.org/b/139412 imported/mozilla/svg/filters/svg-filter-chains/clip-output.svg [ ImageOnlyFailure ]
 webkit.org/b/139414 imported/mozilla/svg/filters/feColorMatrix-1.svg [ ImageOnlyFailure ]
diff --git a/LayoutTests/fast/borders/border-image-fill-no-intrinsic-size-expected.html b/LayoutTests/fast/borders/border-image-fill-no-intrinsic-size-expected.html
new file mode 100644 (file)
index 0000000..5a58d93
--- /dev/null
@@ -0,0 +1,38 @@
+<!DOCTYPE HTML>
+<head>
+  <style>
+    .box {
+      height: 100px;
+      width: 100px;
+      margin: 10px;
+      display: inline-block;
+      background-color: red;
+    }
+    .border {
+      border: 20px solid;
+    }
+    .no-border {
+      border: 0px none;
+    }
+    .border-image-100-intrinsic {
+       border-image: url('resources/svg-border-100x100-intrinsic.svg') 0 fill;
+    }
+    .border-image-100-intrinsic-slice {
+       border-image: url('resources/svg-border-100x100-intrinsic.svg') 20 fill;
+    }
+    .border-image-140-intrinsic-slice {
+       border-image: url('resources/svg-border-140x140-intrinsic.svg') 20 fill;
+    }
+  </style>
+</head>
+<body>
+  <div class="box no-border border-image-100-intrinsic"></div>
+  <div class="box border    border-image-100-intrinsic"></div>
+  <div class="box no-border border-image-100-intrinsic-slice"></div>
+  <div class="box border    border-image-100-intrinsic-slice"></div>
+  <br>
+  <div class="box no-border border-image-100-intrinsic"></div>
+  <div class="box border    border-image-100-intrinsic"></div>
+  <div class="box no-border border-image-100-intrinsic"></div>
+  <div class="box border    border-image-140-intrinsic-slice"></div>
+</body>
diff --git a/LayoutTests/fast/borders/border-image-fill-no-intrinsic-size.html b/LayoutTests/fast/borders/border-image-fill-no-intrinsic-size.html
new file mode 100644 (file)
index 0000000..8696b6f
--- /dev/null
@@ -0,0 +1,41 @@
+<!DOCTYPE HTML>
+<head>
+  <style>
+    .box {
+      height: 100px;
+      width: 100px;
+      margin: 10px;
+      display: inline-block;
+      background-color: red;
+    }
+    .border {
+      border: 20px solid;
+    }
+    .no-border {
+      border: 0px none;
+    }
+    .border-image-100-intrinsic {
+       border-image: url('resources/svg-border-100x100-intrinsic.svg') 0 fill;
+    }
+    .border-image-100-intrinsic-slice {
+       border-image: url('resources/svg-border-100x100-intrinsic.svg') 20 fill;
+    }
+    .border-image-no-intrinsic {
+       border-image: url('resources/svg-border-no-intrinsic.svg') 0 fill;
+    }
+    .border-image-no-intrinsic-slice {
+       border-image: url('resources/svg-border-no-intrinsic.svg') 20 fill;
+    }
+  </style>
+</head>
+<body>
+  <div class="box no-border border-image-100-intrinsic"></div>
+  <div class="box border    border-image-100-intrinsic"></div>
+  <div class="box no-border border-image-100-intrinsic-slice"></div>
+  <div class="box border    border-image-100-intrinsic-slice"></div>
+  <br>
+  <div class="box no-border border-image-no-intrinsic"></div>
+  <div class="box border    border-image-no-intrinsic"></div>
+  <div class="box no-border border-image-no-intrinsic-slice"></div>
+  <div class="box border    border-image-no-intrinsic-slice"></div>
+</body>
diff --git a/LayoutTests/fast/borders/resources/svg-border-100x100-intrinsic.svg b/LayoutTests/fast/borders/resources/svg-border-100x100-intrinsic.svg
new file mode 100644 (file)
index 0000000..588d03a
--- /dev/null
@@ -0,0 +1,4 @@
+<svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="100" height="100">
+  <rect width="100" height="100" fill="lime"/>
+  <rect x="10" y="10" width="80" height="80" fill="none" stroke="black" stroke-width="4px"/>
+</svg>
\ No newline at end of file
diff --git a/LayoutTests/fast/borders/resources/svg-border-140x140-intrinsic.svg b/LayoutTests/fast/borders/resources/svg-border-140x140-intrinsic.svg
new file mode 100644 (file)
index 0000000..9f91404
--- /dev/null
@@ -0,0 +1,52 @@
+<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" width="140" height="140">
+  <defs>
+    <g id="border-image">
+      <rect width="100" height="100" fill="lime"/>
+      <rect x="10" y="10" width="80" height="80" fill="none" stroke="black" stroke-width="4px"/>
+    </g>
+    <clipPath id="top-left">
+      <rect x="0" y="0" width="20" height="20"/>
+    </clipPath>
+    <clipPath id="left">
+      <rect x="0" y="0" width="20" height="100"/>
+    </clipPath>
+    <clipPath id="bottom-left">
+      <rect x="0" y="0" width="20" height="20"/>
+    </clipPath>
+    <clipPath id="top-right">
+      <rect x="0" y="0" width="20" height="20"/>
+    </clipPath>
+    <clipPath id="right">
+      <rect x="0" y="0" width="20" height="100"/>
+    </clipPath>
+    <clipPath id="bottom-right">
+      <rect x="0" y="0" width="20" height="20"/>
+    </clipPath>
+    <clipPath id="top">
+      <rect x="0" y="0" width="100" height="20"/>
+    </clipPath>
+    <clipPath id="bottom">
+      <rect x="0" y="0" width="100" height="20"/>
+    </clipPath>
+    <clipPath id="middle">
+      <rect x="0" y="0" width="100" height="100"/>
+    </clipPath>
+  </defs>
+  
+  <!-- draw left side -->
+  <use x="0" y="0" xlink:href="#border-image" clip-path="url(#top-left)"/>
+  <use x="0" y="20" xlink:href="#border-image" clip-path="url(#left)"/>
+  <use x="0" y="120" xlink:href="#border-image" clip-path="url(#bottom-left)"/>
+  
+  <!-- draw right side -->
+  <use x="120" y="0" xlink:href="#border-image" clip-path="url(#top-right)"/>
+  <use x="120" y="20" xlink:href="#border-image" clip-path="url(#right)"/>
+  <use x="120" y="120" xlink:href="#border-image" clip-path="url(#bottom-right)"/>
+  
+  <!-- draw top and bottom sides -->
+  <use x="20" y="0" xlink:href="#border-image" clip-path="url(#top)"/>
+  <use x="20" y="120" xlink:href="#border-image" clip-path="url(#bottom)"/>
+  
+  <!-- draw middle -->
+  <use x="20" y="20" xlink:href="#border-image" clip-path="url(#middle)"/>
+</svg>
\ No newline at end of file
diff --git a/LayoutTests/fast/borders/resources/svg-border-no-intrinsic.svg b/LayoutTests/fast/borders/resources/svg-border-no-intrinsic.svg
new file mode 100644 (file)
index 0000000..37b14a7
--- /dev/null
@@ -0,0 +1,4 @@
+<svg xmlns="http://www.w3.org/2000/svg" version="1.1">
+  <rect width="100" height="100" fill="lime"/>
+  <rect x="10" y="10" width="80" height="80" fill="none" stroke="black" stroke-width="4px"/>
+</svg>
\ No newline at end of file
index 15c8416a28c73ecf796e6625b4877bd38ee1e68d..c7d885c6394365f8eacc3308d0111e78eaa4fcad 100644 (file)
@@ -1,3 +1,16 @@
+2015-05-26  Said Abou-Hallawa  <sabouhallawa@apple.com>
+
+        An SVG with no intrinsic size does not draw correct slices when used as a border-image for an HTML element.
+        https://bugs.webkit.org/show_bug.cgi?id=139405
+
+        Reviewed by Darin Adler.
+
+        * svg/as-image/border-image-simple-2.html: Add "border: 0px none;" to
+        style of the <div> although the style has "border-image: url() 0 fill;".
+        If the border width is not set to zero in the style, the <div> will have
+        a 3px border. This seems to be a bug in WebKit but should be unrelated to
+        the non-intrinsic-sized images with border-image.
+
 2014-12-09  Said Abou-Hallawa  <sabouhallawa@apple.com>
 
         Import Mozilla test suite for SVG.
index fca68d6133b20434ddd06963ef11b8792a765319..7fe5a64159df205fe524b1ffdf76bbe20d15b870 100644 (file)
@@ -1,6 +1,6 @@
 <html>
 <body>
-  <div style="height: 100px; width: 100px;
+  <div style="height: 100px; width: 100px; border: 0px none;
               border-image: url('resources/lime100x100-noSVGDimensions.svg') 0 fill;"/>
 </body>
 </html>
index 97a3d206962c21746b58e6cebcb9a2d4fc31ce17..a5903388faa6faf80461d50e3996a1d6b18fb762 100644 (file)
@@ -2044,7 +2044,6 @@ set(WebCore_SOURCES
     platform/KillRingNone.cpp
     platform/Language.cpp
     platform/Length.cpp
-    platform/LengthBox.cpp
     platform/LinkHash.cpp
     platform/Logging.cpp
     platform/MIMETypeRegistry.cpp
@@ -2151,7 +2150,6 @@ set(WebCore_SOURCES
     platform/graphics/IntRect.cpp
     platform/graphics/IntSize.cpp
     platform/graphics/ISOVTTCue.cpp
-    platform/graphics/LayoutBoxExtent.cpp
     platform/graphics/LayoutRect.cpp
     platform/graphics/MaskImageOperation.cpp
     platform/graphics/MediaPlayer.cpp
index fc4e6a1af4be12a366118af3d5c7785fe7c0e686..da88d7d589f1d5e14f52c36e1f5677759ac7d5af 100644 (file)
@@ -1,3 +1,167 @@
+2015-05-26  Said Abou-Hallawa  <sabouhallawa@apple.com>
+
+        An SVG with no intrinsic size does not draw correct slices when used as a border-image for an HTML element.
+        https://bugs.webkit.org/show_bug.cgi?id=139405
+
+        Reviewed by Darin Adler.
+        
+        When using a non-intrinsic-sized image as an image-border, all the source
+        slices have to be extracted from the top-left corner of the source image.
+        This is because the right and bottom sides of the image can not be known.
+        Also all the slices should not be stretched. In other words, the sizes of
+        source slices for a non-intrinsic-sized image should be equal to the sizes
+        of the destination container slices.
+
+        This is not compliant with the css3 w3c specs. I think the specs makes it
+        harder to predict what exactly will be drawn for the image-border in this
+        case. See http://www.w3.org/TR/css3-background/#border-image-slice. This
+        approach is implemented by FireFox. And I think it gives a more predictable 
+        rendering for image-border in the case of non-intrinsic-sized images.
+        
+        Test: fast/borders/border-image-fill-no-intrinsic-size.html
+
+        * CMakeLists.txt:
+        * WebCore.vcxproj/WebCore.vcxproj:
+        * WebCore.vcxproj/WebCore.vcxproj.filters:
+        * WebCore.xcodeproj/project.pbxproj:
+        * platform/LengthBox.cpp: Removed.
+        * platform/graphics/LayoutBoxExtent.cpp: Removed.
+        * platform/graphics/LayoutBoxExtent.h: Removed.
+        * platform/graphics/LayoutRect.h:
+        Delete LengthBox.cpp and move all the functionalities to LengthBox.h.
+        Delete LayoutBoxExtent.cpp since it is the same class as LengthBox.
+        
+        * css/CSSProperty.cpp:
+        * platform/text/WritingMode.h:
+        Move the enums LogicalBoxSide and PhysicalBoxSide
+        from CSSProperty.cpp to WritingMode.h so it can be used by other classes.
+        
+        * css/CSSToStyleMap.cpp:
+        (WebCore::CSSToStyleMap::mapNinePieceImageSlice):
+        (WebCore::CSSToStyleMap::mapNinePieceImageQuad):
+        * css/CSSToStyleMap.h:
+        * inspector/InspectorOverlay.cpp:
+        (WebCore::buildRendererHighlight):
+        * rendering/InlineFlowBox.cpp:
+        (WebCore::InlineFlowBox::addBorderOutsetVisualOverflow):
+        * rendering/RenderBox.h:
+        (WebCore::RenderBox::marginLogicalLeft):
+        (WebCore::RenderBox::marginLogicalRight):
+        (WebCore::RenderBox::setMarginBefore):
+        (WebCore::RenderBox::setMarginAfter):
+        (WebCore::RenderBox::setMarginStart):
+        (WebCore::RenderBox::setMarginEnd):
+        * rendering/style/RenderStyle.cpp:
+        (WebCore::RenderStyle::setClip):
+        (WebCore::RenderStyle::noneDashboardRegions):
+        * rendering/style/RenderStyle.h:
+        Use the new BoxExtent access methods for getting and settings the sides of
+        LengthBox and LayoutBoxExtent.
+        
+        * platform/LengthBox.h:
+        (WebCore::BoxExtent::BoxExtent):
+        (WebCore::BoxExtent::at):
+        (WebCore::BoxExtent::top):
+        (WebCore::BoxExtent::right):
+        (WebCore::BoxExtent::bottom):
+        (WebCore::BoxExtent::left):
+        (WebCore::BoxExtent::setAt):
+        (WebCore::BoxExtent::setTop):
+        (WebCore::BoxExtent::setRight):
+        (WebCore::BoxExtent::setBottom):
+        (WebCore::BoxExtent::setLeft):
+        (WebCore::BoxExtent::before):
+        (WebCore::BoxExtent::end):
+        (WebCore::BoxExtent::after):
+        (WebCore::BoxExtent::start):
+        (WebCore::BoxExtent::setBefore):
+        (WebCore::BoxExtent::setEnd):
+        (WebCore::BoxExtent::setAfter):
+        (WebCore::BoxExtent::setStart):
+        (WebCore::BoxExtent::operator==):
+        (WebCore::BoxExtent::operator!=):
+        (WebCore::LengthBox::LengthBox):
+        (WebCore::LengthBox::isZero):
+        (WebCore::LengthBox::left): Deleted.
+        (WebCore::LengthBox::right): Deleted.
+        (WebCore::LengthBox::top): Deleted.
+        (WebCore::LengthBox::bottom): Deleted.
+        (WebCore::LengthBox::operator==): Deleted.
+        (WebCore::LengthBox::operator!=): Deleted.
+        (WebCore::LengthBox::nonZero): Deleted.
+        Define a new template class for 'BoxExtent'. A 'BoxExtent' represents the
+        extent of four sides of a box. Use this class template to define the exiting 
+        classes 'LengthBox' and 'LayoutBoxExtent'. Use it also to and define the
+        new class FloatBoxExtent
+            
+        * rendering/RenderBoxModelObject.cpp:
+        (WebCore::RenderBoxModelObject::calculateImageIntrinsicDimensions):
+        * rendering/RenderBoxModelObject.h:
+        (WebCore::RenderBoxModelObject::calculateFillTileSize):
+        * rendering/RenderListMarker.cpp:
+        (WebCore::RenderListMarker::updateContent):
+        * rendering/shapes/ShapeOutsideInfo.cpp:
+        (WebCore::ShapeOutsideInfo::createShapeForImage):
+        Change the return value of calculateImageIntrinsicDimensions() to be a
+        bool which indicates whether the image has an intrinsic size or not. Add
+        a new reference argument to this function receive the resolved image size.
+        
+        (WebCore::RenderBoxModelObject::paintNinePieceImage): Move all the painting
+        code of this function to NinePieceImage::paint()
+        
+        (WebCore::computeBorderImageSide): Deleted.
+        Renamed to be NinePieceImage::computeSlice().
+        
+        * rendering/style/BorderData.h:
+        (WebCore::BorderData::borderWidth): Add a new method to return the extents
+        of the border in a FloatBoxExtent.
+        
+        * rendering/style/NinePieceImage.cpp:
+        (WebCore::NinePieceImage::computeSlice): Moved from NinePieceImage::computeSlice().
+        
+        (WebCore::NinePieceImage::computeSlices): The first version of this function
+        computes the slices given their lengths. The slices have to be clamped to
+        the container size. The second version of this function computes the slices
+        given their lengths, their actual extents and their source slices.
+        
+        (WebCore::NinePieceImage::scaleSlicesIfNeeded):  Reduce the slices if they
+        are too large.
+        
+        (WebCore::NinePieceImage::isEmptyPieceRect): Returns true if an ImagePiece
+        should not be drawn.
+        
+        (WebCore::NinePieceImage::horizontalTileRules):
+        (WebCore::NinePieceImage::verticalTileRules):
+        Fill vectors of tiling rules to be passed to GraphicsContext::drawTiledImage()
+        
+        (WebCore::NinePieceImage::computeIntrinsicRects): Computes the nine pieces
+        rectangles for an intrinsic-sized container.
+        
+        (WebCore::NinePieceImage::computeNonIntrinsicRects): Computes the nine
+        pieces rectangles for an non-intrinsic-sized source image. The computed
+        rectangles have to start at (0, 0) and their sizes should be equal to
+        the sizes of the nine pieces rectangles of the destination container.
+        
+        (WebCore::NinePieceImage::computeIntrinsicSideTileScale):
+        (WebCore::NinePieceImage::computeIntrinsicMiddleTileScale):
+        (WebCore::NinePieceImage::computeIntrinsicTileScales):
+        (WebCore::NinePieceImage::computeNonIntrinsicTileScales):
+        Computes the scaling factors for drawing the tiles. For non-intrinsic source
+        images, there should not be any scaling factors. 
+        
+        (WebCore::NinePieceImage::paint): Moved from RenderBoxModelObject::paintNinePieceImage()
+        but simplified and restructured.
+        
+        (WebCore::NinePieceImageData::NinePieceImageData): Use nullptr instead of 0.
+        
+        * rendering/style/NinePieceImage.h:
+        (WebCore::operator++):
+        (WebCore::isCornerPiece): 
+        (WebCore::isMiddlePiece):
+        (WebCore::imagePieceHorizontalSide):
+        (WebCore::imagePieceVerticalSide):
+        Add helper functions for the enum ImagePiece.
+
 2015-05-26  Andreas Kling  <akling@apple.com>
 
         <font face> doesn't support plus character in font family names.
index 7842de0245afedcc56d93fc7b0bb5f0d58db8c21..2383548199582a5b1481b05a10cd899e55d33803 100644 (file)
     <ClCompile Include="..\platform\URL.cpp" />
     <ClCompile Include="..\platform\Language.cpp" />
     <ClCompile Include="..\platform\Length.cpp" />
-    <ClCompile Include="..\platform\LengthBox.cpp" />
     <ClCompile Include="..\platform\LinkHash.cpp" />
     <ClCompile Include="..\platform\LocalizedStrings.cpp" />
     <ClCompile Include="..\platform\Logging.cpp" />
     <ClCompile Include="..\platform\graphics\IntPoint.cpp" />
     <ClCompile Include="..\platform\graphics\IntRect.cpp" />
     <ClCompile Include="..\platform\graphics\IntSize.cpp" />
-    <ClCompile Include="..\platform\graphics\LayoutBoxExtent.cpp" />
     <ClCompile Include="..\platform\graphics\LayoutRect.cpp" />
     <ClCompile Include="..\platform\graphics\MediaPlayer.cpp" />
     <ClCompile Include="..\platform\graphics\Path.cpp" />
     <ClInclude Include="..\platform\graphics\IntSize.h" />
     <ClInclude Include="..\platform\graphics\IntSizeHash.h" />
     <ClInclude Include="..\platform\graphics\ISOVTTCue.h" />
-    <ClInclude Include="..\platform\graphics\LayoutBoxExtent.h" />
     <ClInclude Include="..\platform\graphics\LayoutPoint.h" />
     <ClInclude Include="..\platform\graphics\LayoutRect.h" />
     <ClInclude Include="..\platform\graphics\LayoutSize.h" />
index 78ff511e25a1c3980b4800e002238fd7479d58b2..55dcaf6f1ebcdebe0317f6f2bcdf97776c55275e 100644 (file)
     <ClCompile Include="..\platform\Length.cpp">
       <Filter>platform</Filter>
     </ClCompile>
-    <ClCompile Include="..\platform\LengthBox.cpp">
-      <Filter>platform</Filter>
-    </ClCompile>
     <ClCompile Include="..\platform\LinkHash.cpp">
       <Filter>platform</Filter>
     </ClCompile>
     <ClCompile Include="..\platform\graphics\IntSize.cpp">
       <Filter>platform\graphics</Filter>
     </ClCompile>
-    <ClCompile Include="..\platform\graphics\LayoutBoxExtent.cpp">
-      <Filter>platform\graphics</Filter>
-    </ClCompile>
     <ClCompile Include="..\platform\graphics\LayoutRect.cpp">
       <Filter>platform\graphics</Filter>
     </ClCompile>
     <ClInclude Include="..\platform\graphics\IntSizeHash.h">
       <Filter>platform\graphics</Filter>
     </ClInclude>
-    <ClInclude Include="..\platform\graphics\LayoutBoxExtent.h">
-      <Filter>platform\graphics</Filter>
-    </ClInclude>
     <ClInclude Include="..\platform\graphics\LayoutPoint.h">
       <Filter>platform\graphics</Filter>
     </ClInclude>
index 37e477c8c83cf75cd7fe1d4818ef4db3205f0761..b440acd7b7e2a45ace5842e7626f5500dd78a827 100644 (file)
                14115B7309F84CD600CA4FC1 /* JSNodeFilter.h in Headers */ = {isa = PBXBuildFile; fileRef = 14115B7109F84CD600CA4FC1 /* JSNodeFilter.h */; };
                1411DCB1164C39A800D49BC1 /* WidthCache.h in Headers */ = {isa = PBXBuildFile; fileRef = 1411DCB0164C39A800D49BC1 /* WidthCache.h */; settings = {ATTRIBUTES = (Private, ); }; };
                141DC0481648348F00371E5A /* LayoutUnit.h in Headers */ = {isa = PBXBuildFile; fileRef = 141DC0471648348F00371E5A /* LayoutUnit.h */; settings = {ATTRIBUTES = (Private, ); }; };
-               141DC04F164834B900371E5A /* LayoutBoxExtent.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 141DC049164834B900371E5A /* LayoutBoxExtent.cpp */; };
-               141DC050164834B900371E5A /* LayoutBoxExtent.h in Headers */ = {isa = PBXBuildFile; fileRef = 141DC04A164834B900371E5A /* LayoutBoxExtent.h */; settings = {ATTRIBUTES = (Private, ); }; };
                141DC051164834B900371E5A /* LayoutPoint.h in Headers */ = {isa = PBXBuildFile; fileRef = 141DC04B164834B900371E5A /* LayoutPoint.h */; settings = {ATTRIBUTES = (Private, ); }; };
                141DC052164834B900371E5A /* LayoutRect.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 141DC04C164834B900371E5A /* LayoutRect.cpp */; };
                141DC053164834B900371E5A /* LayoutRect.h in Headers */ = {isa = PBXBuildFile; fileRef = 141DC04D164834B900371E5A /* LayoutRect.h */; settings = {ATTRIBUTES = (Private, ); }; };
                14476AA815DC4BB100305DB2 /* WritingMode.h in Headers */ = {isa = PBXBuildFile; fileRef = 14476AA715DC4BB100305DB2 /* WritingMode.h */; settings = {ATTRIBUTES = (Private, ); }; };
                1449E24C107D4A8400B5793F /* JSCallbackData.h in Headers */ = {isa = PBXBuildFile; fileRef = 1449E24A107D4A8400B5793F /* JSCallbackData.h */; };
                1449E287107D4DB400B5793F /* JSCallbackData.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 1449E286107D4DB400B5793F /* JSCallbackData.cpp */; };
-               146CC115156988E400109E37 /* LengthBox.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 146CC113156988BD00109E37 /* LengthBox.cpp */; };
                1477E7760BF4134A00152872 /* PageCache.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 1477E7740BF4134A00152872 /* PageCache.cpp */; };
                1477E7770BF4134A00152872 /* PageCache.h in Headers */ = {isa = PBXBuildFile; fileRef = 1477E7750BF4134A00152872 /* PageCache.h */; settings = {ATTRIBUTES = (Private, ); }; };
                1479FAED109AE37500DED655 /* RenderRuby.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 1479FAE5109AE37500DED655 /* RenderRuby.cpp */; };
                141B94E509EC4223000E9413 /* MouseEvent.idl */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = MouseEvent.idl; sourceTree = "<group>"; };
                141B94EE09EC425A000E9413 /* UIEvent.idl */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = UIEvent.idl; sourceTree = "<group>"; };
                141DC0471648348F00371E5A /* LayoutUnit.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LayoutUnit.h; sourceTree = "<group>"; };
-               141DC049164834B900371E5A /* LayoutBoxExtent.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LayoutBoxExtent.cpp; sourceTree = "<group>"; };
-               141DC04A164834B900371E5A /* LayoutBoxExtent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LayoutBoxExtent.h; sourceTree = "<group>"; };
                141DC04B164834B900371E5A /* LayoutPoint.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LayoutPoint.h; sourceTree = "<group>"; };
                141DC04C164834B900371E5A /* LayoutRect.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LayoutRect.cpp; sourceTree = "<group>"; };
                141DC04D164834B900371E5A /* LayoutRect.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = LayoutRect.h; sourceTree = "<group>"; };
                14476AA715DC4BB100305DB2 /* WritingMode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WritingMode.h; sourceTree = "<group>"; };
                1449E24A107D4A8400B5793F /* JSCallbackData.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSCallbackData.h; sourceTree = "<group>"; };
                1449E286107D4DB400B5793F /* JSCallbackData.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSCallbackData.cpp; sourceTree = "<group>"; };
-               146CC113156988BD00109E37 /* LengthBox.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = LengthBox.cpp; sourceTree = "<group>"; };
                1477E7740BF4134A00152872 /* PageCache.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = PageCache.cpp; sourceTree = "<group>"; };
                1477E7750BF4134A00152872 /* PageCache.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = PageCache.h; sourceTree = "<group>"; };
                1479FAE5109AE37500DED655 /* RenderRuby.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RenderRuby.cpp; sourceTree = "<group>"; };
                                07AC46FF1952102100EE9723 /* ISOVTTCue.cpp */,
                                07AC47001952102100EE9723 /* ISOVTTCue.h */,
                                65CC6BED16014EC0000ED27D /* Latin1TextIterator.h */,
-                               141DC049164834B900371E5A /* LayoutBoxExtent.cpp */,
-                               141DC04A164834B900371E5A /* LayoutBoxExtent.h */,
                                141DC04B164834B900371E5A /* LayoutPoint.h */,
                                141DC04C164834B900371E5A /* LayoutRect.cpp */,
                                141DC04D164834B900371E5A /* LayoutRect.h */,
                                141DC0471648348F00371E5A /* LayoutUnit.h */,
                                BCE65BE80EACDF16007E4533 /* Length.cpp */,
                                BCE65BE90EACDF16007E4533 /* Length.h */,
-                               146CC113156988BD00109E37 /* LengthBox.cpp */,
                                BCFF648F0EAD15C200C1D6F7 /* LengthBox.h */,
                                BCFF64900EAD15C200C1D6F7 /* LengthSize.h */,
                                A7AD2F850EC89D07008AB002 /* LinkHash.cpp */,
                                E4916FF7195DF6A0005AB349 /* LayerFlushThrottleState.h in Headers */,
                                580371641A66F1D300BAF519 /* LayerFragment.h in Headers */,
                                7AA3A6A0194B59B6001CBD24 /* LayerPool.h in Headers */,
-                               141DC050164834B900371E5A /* LayoutBoxExtent.h in Headers */,
                                931D72F615FE695300C4C07E /* LayoutMilestones.h in Headers */,
                                141DC051164834B900371E5A /* LayoutPoint.h in Headers */,
                                141DC053164834B900371E5A /* LayoutRect.h in Headers */,
                                2917B5611473496C0052C9D0 /* LayerFlushScheduler.cpp in Sources */,
                                2917B566147349950052C9D0 /* LayerFlushSchedulerMac.cpp in Sources */,
                                7AA3A69F194B59B6001CBD24 /* LayerPool.cpp in Sources */,
-                               141DC04F164834B900371E5A /* LayoutBoxExtent.cpp in Sources */,
                                141DC052164834B900371E5A /* LayoutRect.cpp in Sources */,
                                A120ACA413F998CA00FE4AC7 /* LayoutRepainter.cpp in Sources */,
                                2D9066060BE141D400956998 /* LayoutState.cpp in Sources */,
                                512DD8F40D91E6AF000F89EE /* LegacyWebArchive.cpp in Sources */,
                                51B2417B0D931F3F00E83F5C /* LegacyWebArchiveMac.mm in Sources */,
                                BCE65BEA0EACDF16007E4533 /* Length.cpp in Sources */,
-                               146CC115156988E400109E37 /* LengthBox.cpp in Sources */,
                                E55F497A151B888000BB67DB /* LengthFunctions.cpp in Sources */,
                                FFB698CC1833EE0D00158A31 /* LineBreaker.cpp in Sources */,
                                89B5EAA111E8003D00F2367E /* LineEnding.cpp in Sources */,
index e12673d184825b23b491ccbf0ba230577cf6533d..a62fbcc16ecbbb401b04f14d2afbcedbfd7ca8a8 100644 (file)
@@ -54,9 +54,6 @@ void CSSProperty::wrapValueInCommaSeparatedList()
     m_value = WTF::move(list);
 }
 
-enum LogicalBoxSide { BeforeSide, EndSide, AfterSide, StartSide };
-enum PhysicalBoxSide { TopSide, RightSide, BottomSide, LeftSide };
-
 static CSSPropertyID resolveToPhysicalProperty(TextDirection direction, WritingMode writingMode, LogicalBoxSide logicalSide, const StylePropertyShorthand& shorthand)
 {
     if (direction == LTR) {
index e5c8baa70b42cc8afcb57491eaaf668e28f16065..27d53051003f22a247ed41fa3e628709e18327d9 100644 (file)
@@ -618,21 +618,21 @@ void CSSToStyleMap::mapNinePieceImageSlice(CSSValue& value, NinePieceImage& imag
     LengthBox box;
     Quad* slices = borderImageSlice.slices();
     if (slices->top()->isPercentage())
-        box.m_top = Length(slices->top()->getDoubleValue(), Percent);
+        box.top() = Length(slices->top()->getDoubleValue(), Percent);
     else
-        box.m_top = Length(slices->top()->getIntValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
+        box.top() = Length(slices->top()->getIntValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
     if (slices->bottom()->isPercentage())
-        box.m_bottom = Length(slices->bottom()->getDoubleValue(), Percent);
+        box.bottom() = Length(slices->bottom()->getDoubleValue(), Percent);
     else
-        box.m_bottom = Length((int)slices->bottom()->getFloatValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
+        box.bottom() = Length((int)slices->bottom()->getFloatValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
     if (slices->left()->isPercentage())
-        box.m_left = Length(slices->left()->getDoubleValue(), Percent);
+        box.left() = Length(slices->left()->getDoubleValue(), Percent);
     else
-        box.m_left = Length(slices->left()->getIntValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
+        box.left() = Length(slices->left()->getIntValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
     if (slices->right()->isPercentage())
-        box.m_right = Length(slices->right()->getDoubleValue(), Percent);
+        box.right() = Length(slices->right()->getDoubleValue(), Percent);
     else
-        box.m_right = Length(slices->right()->getIntValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
+        box.right() = Length(slices->right()->getIntValue(CSSPrimitiveValue::CSS_NUMBER), Fixed);
     image.setImageSlices(box);
 
     // Set our fill mode.
@@ -654,32 +654,32 @@ LengthBox CSSToStyleMap::mapNinePieceImageQuad(CSSValue& value)
     LengthBox box; // Defaults to 'auto' so we don't have to handle that explicitly below.
     Quad* slices = borderWidths.getQuadValue();
     if (slices->top()->isNumber())
-        box.m_top = Length(slices->top()->getIntValue(), Relative);
+        box.top() = Length(slices->top()->getIntValue(), Relative);
     else if (slices->top()->isPercentage())
-        box.m_top = Length(slices->top()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
+        box.top() = Length(slices->top()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
     else if (slices->top()->getValueID() != CSSValueAuto)
-        box.m_top = slices->top()->computeLength<Length>(conversionData);
+        box.top() = slices->top()->computeLength<Length>(conversionData);
 
     if (slices->right()->isNumber())
-        box.m_right = Length(slices->right()->getIntValue(), Relative);
+        box.right() = Length(slices->right()->getIntValue(), Relative);
     else if (slices->right()->isPercentage())
-        box.m_right = Length(slices->right()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
+        box.right() = Length(slices->right()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
     else if (slices->right()->getValueID() != CSSValueAuto)
-        box.m_right = slices->right()->computeLength<Length>(conversionData);
+        box.right() = slices->right()->computeLength<Length>(conversionData);
 
     if (slices->bottom()->isNumber())
-        box.m_bottom = Length(slices->bottom()->getIntValue(), Relative);
+        box.bottom() = Length(slices->bottom()->getIntValue(), Relative);
     else if (slices->bottom()->isPercentage())
-        box.m_bottom = Length(slices->bottom()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
+        box.bottom() = Length(slices->bottom()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
     else if (slices->bottom()->getValueID() != CSSValueAuto)
-        box.m_bottom = slices->bottom()->computeLength<Length>(conversionData);
+        box.bottom() = slices->bottom()->computeLength<Length>(conversionData);
 
     if (slices->left()->isNumber())
-        box.m_left = Length(slices->left()->getIntValue(), Relative);
+        box.left() = Length(slices->left()->getIntValue(), Relative);
     else if (slices->left()->isPercentage())
-        box.m_left = Length(slices->left()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
+        box.left() = Length(slices->left()->getDoubleValue(CSSPrimitiveValue::CSS_PERCENTAGE), Percent);
     else if (slices->left()->getValueID() != CSSValueAuto)
-        box.m_left = slices->left()->computeLength<Length>(conversionData);
+        box.left() = slices->left()->computeLength<Length>(conversionData);
 
     return box;
 }
index 0ae129570b498ef1a121745e4e178de55353f265..259eb2616ebc88f728be8056a92cb3af22a98b3e 100644 (file)
@@ -36,7 +36,7 @@ class StyleImage;
 class StyleResolver;
 class NinePieceImage;
 
-struct LengthBox;
+class LengthBox;
 
 class CSSToStyleMap {
     WTF_MAKE_NONCOPYABLE(CSSToStyleMap);
index 282a1603786c637805d2233b07e1769993c79553..25ed16bcd86e2384ed265d09fbcb3ad628eec7bc 100644 (file)
@@ -111,8 +111,8 @@ static void buildRendererHighlight(RenderObject* renderer, RenderRegion* region,
             if (!renderBox.isOutOfFlowPositioned() && region) {
                 RenderBox::LogicalExtentComputedValues computedValues;
                 renderBox.computeLogicalWidthInRegion(computedValues, region);
-                margins.mutableLogicalLeft(renderBox.style().writingMode()) = computedValues.m_margins.m_start;
-                margins.mutableLogicalRight(renderBox.style().writingMode()) = computedValues.m_margins.m_end;
+                margins.start(renderBox.style().writingMode()) = computedValues.m_margins.m_start;
+                margins.end(renderBox.style().writingMode()) = computedValues.m_margins.m_end;
             }
 
             paddingBox = renderBox.clientBoxRectInRegion(region);
diff --git a/Source/WebCore/platform/LengthBox.cpp b/Source/WebCore/platform/LengthBox.cpp
deleted file mode 100644 (file)
index 2406903..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright (c) 2012, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- *     * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *     * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- *     * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "LengthBox.h"
-
-namespace WebCore {
-
-const Length& LengthBox::logicalLeft(WritingMode writingMode) const
-{
-    return isHorizontalWritingMode(writingMode) ? m_left : m_top;
-}
-
-const Length& LengthBox::logicalRight(WritingMode writingMode) const
-{
-    return isHorizontalWritingMode(writingMode) ? m_right : m_bottom;
-}
-
-const Length& LengthBox::before(WritingMode writingMode) const
-{
-    switch (writingMode) {
-    case TopToBottomWritingMode:
-        return m_top;
-    case BottomToTopWritingMode:
-        return m_bottom;
-    case LeftToRightWritingMode:
-        return m_left;
-    case RightToLeftWritingMode:
-        return m_right;
-    }
-    ASSERT_NOT_REACHED();
-    return m_top;
-}
-
-const Length& LengthBox::after(WritingMode writingMode) const
-{
-    switch (writingMode) {
-    case TopToBottomWritingMode:
-        return m_bottom;
-    case BottomToTopWritingMode:
-        return m_top;
-    case LeftToRightWritingMode:
-        return m_right;
-    case RightToLeftWritingMode:
-        return m_left;
-    }
-    ASSERT_NOT_REACHED();
-    return m_bottom;
-}
-
-const Length& LengthBox::start(WritingMode writingMode, TextDirection direction) const
-{
-    if (isHorizontalWritingMode(writingMode))
-        return isLeftToRightDirection(direction) ? m_left : m_right;
-    return isLeftToRightDirection(direction) ? m_top : m_bottom;
-}
-
-const Length& LengthBox::end(WritingMode writingMode, TextDirection direction) const
-{
-    if (isHorizontalWritingMode(writingMode))
-        return isLeftToRightDirection(direction) ? m_right : m_left;
-    return isLeftToRightDirection(direction) ? m_bottom : m_top;
-}
-
-} // namespace WebCore
index 105f07986ca62b0b4dbc5da0d1c1463667b3bb4c..34195ee797b1b9b342f737e532988595ad10fb3b 100644 (file)
@@ -1,6 +1,6 @@
 /*
     Copyright (C) 1999 Lars Knoll (knoll@kde.org)
-    Copyright (C) 2006, 2008 Apple Inc. All rights reserved.
+    Copyright (C) 2006, 2008, 2015 Apple Inc. All rights reserved.
     Copyright (c) 2012, Google Inc. All rights reserved.
 
     This library is free software; you can redistribute it and/or
 #include "Length.h"
 #include "TextFlags.h"
 #include "WritingMode.h"
+#include <array>
 
 namespace WebCore {
 
-struct LengthBox {
-    LengthBox()
+template<typename T> class BoxExtent {
+public:
+    BoxExtent()
+        : m_sides({{ T(0), T(0), T(0), T(0) }})
     {
     }
 
-    explicit LengthBox(LengthType type)
-        : m_left(type)
-        , m_right(type)
-        , m_top(type)
-        , m_bottom(type)
+    BoxExtent(const T& top, const T& right, const T& bottom, const T& left)
+        : m_sides({{ top, right, bottom, left }})
     {
     }
 
-    explicit LengthBox(int v)
-        : m_left(Length(v, Fixed))
-        , m_right(Length(v, Fixed))
-        , m_top(Length(v, Fixed))
-        , m_bottom(Length(v, Fixed))
+    T& at(PhysicalBoxSide side) { return m_sides[side]; }
+    T& top() { return at(TopSide); }
+    T& right() { return at(RightSide); }
+    T& bottom() { return at(BottomSide); }
+    T& left() { return at(LeftSide); }
+
+    const T& at(PhysicalBoxSide side) const { return m_sides[side]; }
+    const T& top() const { return at(TopSide); }
+    const T& right() const { return at(RightSide); }
+    const T& bottom() const { return at(BottomSide); }
+    const T& left() const { return at(LeftSide); }
+
+    void setAt(PhysicalBoxSide side, const T& v) { at(side) = v; }
+    void setTop(const T& top) { setAt(TopSide, top); }
+    void setRight(const T& right) { setAt(RightSide, right); }
+    void setBottom(const T& bottom) { setAt(BottomSide, bottom); }
+    void setLeft(const T& left) { setAt(LeftSide, left); }
+
+    T& before(WritingMode writingMode)
     {
+        return isHorizontalWritingMode(writingMode) ?
+            (isFlippedBlocksWritingMode(writingMode) ? bottom() : top()) :
+            (isFlippedBlocksWritingMode(writingMode) ? right() : left());
     }
 
-    LengthBox(Length top, Length right, Length bottom, Length left)
-        : m_left(WTF::move(left))
-        , m_right(WTF::move(right))
-        , m_top(WTF::move(top))
-        , m_bottom(WTF::move(bottom))
+    T& after(WritingMode writingMode)
     {
+        return isHorizontalWritingMode(writingMode) ?
+            (isFlippedBlocksWritingMode(writingMode) ? top() : bottom()) :
+            (isFlippedBlocksWritingMode(writingMode) ? left() : right());
     }
 
-    LengthBox(int top, int right, int bottom, int left)
-        : m_left(Length(left, Fixed))
-        , m_right(Length(right, Fixed))
-        , m_top(Length(top, Fixed))
-        , m_bottom(Length(bottom, Fixed))
+    T& start(WritingMode writingMode, TextDirection direction = LTR)
+    {
+        return isHorizontalWritingMode(writingMode) ?
+            (isLeftToRightDirection(direction) ? left() : right()) :
+            (isLeftToRightDirection(direction) ? top() : bottom());
+    }
+
+    T& end(WritingMode writingMode, TextDirection direction = LTR)
+    {
+        return isHorizontalWritingMode(writingMode) ?
+            (isLeftToRightDirection(direction) ? right() : left()) :
+            (isLeftToRightDirection(direction) ? bottom() : top());
+    }
+
+    const T& before(WritingMode writingMode) const
+    {
+        return isHorizontalWritingMode(writingMode) ?
+            (isFlippedBlocksWritingMode(writingMode) ? bottom() : top()) :
+            (isFlippedBlocksWritingMode(writingMode) ? right() : left());
+    }
+
+    const T& after(WritingMode writingMode) const
+    {
+        return isHorizontalWritingMode(writingMode) ?
+            (isFlippedBlocksWritingMode(writingMode) ? top() : bottom()) :
+            (isFlippedBlocksWritingMode(writingMode) ? left() : right());
+    }
+
+    const T& start(WritingMode writingMode, TextDirection direction = LTR) const
+    {
+        return isHorizontalWritingMode(writingMode) ?
+            (isLeftToRightDirection(direction) ? left() : right()) :
+            (isLeftToRightDirection(direction) ? top() : bottom());
+    }
+
+    const T& end(WritingMode writingMode, TextDirection direction = LTR) const
     {
+        return isHorizontalWritingMode(writingMode) ?
+            (isLeftToRightDirection(direction) ? right() : left()) :
+            (isLeftToRightDirection(direction) ? bottom() : top());
     }
 
-    const Length& left() const { return m_left; }
-    const Length& right() const { return m_right; }
-    const Length& top() const { return m_top; }
-    const Length& bottom() const { return m_bottom; }
+    void setBefore(const T& before, WritingMode writingMode) { this->before(writingMode) = before; }
+    void setAfter(const T& after, WritingMode writingMode) { this->after(writingMode) = after; }
+    void setStart(const T& start, WritingMode writingMode, TextDirection direction = LTR) { this->start(writingMode, direction) = start; }
+    void setEnd(const T& end, WritingMode writingMode, TextDirection direction = LTR) { this->end(writingMode, direction) = end; }
 
-    const Length& logicalLeft(WritingMode) const;
-    const Length& logicalRight(WritingMode) const;
+    bool operator==(const BoxExtent& other) const
+    {
+        return m_sides == other.m_sides;
+    }
+
+    bool operator!=(const BoxExtent& other) const
+    {
+        return m_sides != other.m_sides;
+    }
 
-    const Length& before(WritingMode) const;
-    const Length& after(WritingMode) const;
-    const Length& start(WritingMode, TextDirection) const;
-    const Length& end(WritingMode, TextDirection) const;
+protected:
+    std::array<T, 4> m_sides;
+};
 
-    bool operator==(const LengthBox& other) const
+class LengthBox : public BoxExtent<Length> {
+public:
+    LengthBox()
+        : LengthBox(Auto)
     {
-        return m_left == other.m_left && m_right == other.m_right && m_top == other.m_top && m_bottom == other.m_bottom;
     }
 
-    bool operator!=(const LengthBox& other) const
+    explicit LengthBox(LengthType type)
+        : BoxExtent(Length(type), Length(type), Length(type), Length(type))
     {
-        return !(*this == other);
     }
 
-    bool nonZero() const
+    explicit LengthBox(int v)
+        : BoxExtent(Length(v, Fixed), Length(v, Fixed), Length(v, Fixed), Length(v, Fixed))
     {
-        return !(m_left.isZero() && m_right.isZero() && m_top.isZero() && m_bottom.isZero());
     }
 
-    Length m_left;
-    Length m_right;
-    Length m_top;
-    Length m_bottom;
+    LengthBox(int top, int right, int bottom, int left)
+        : BoxExtent(Length(top, Fixed), Length(right, Fixed), Length(bottom, Fixed), Length(left, Fixed))
+    {
+    }
+
+    LengthBox(const Length& top, const Length& right, const Length& bottom, const Length& left)
+        : BoxExtent(top, right, bottom, left)
+    {
+    }
+
+    bool isZero() const
+    {
+        return top().isZero() && right().isZero() && bottom().isZero() && left().isZero();
+    }
 };
 
+typedef BoxExtent<LayoutUnit> LayoutBoxExtent;
+typedef BoxExtent<float> FloatBoxExtent;
+
 } // namespace WebCore
 
 #endif // LengthBox_h
diff --git a/Source/WebCore/platform/graphics/LayoutBoxExtent.cpp b/Source/WebCore/platform/graphics/LayoutBoxExtent.cpp
deleted file mode 100644 (file)
index fc1c863..0000000
+++ /dev/null
@@ -1,196 +0,0 @@
-/*
- * Copyright (c) 2012, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- *     * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *     * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- *     * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "LayoutBoxExtent.h"
-
-namespace WebCore {
-
-LayoutUnit LayoutBoxExtent::logicalTop(WritingMode writingMode) const
-{
-    return isHorizontalWritingMode(writingMode) ? m_top : m_left;
-}
-
-LayoutUnit LayoutBoxExtent::logicalBottom(WritingMode writingMode) const
-{
-    return isHorizontalWritingMode(writingMode) ? m_bottom : m_right;
-}
-
-LayoutUnit LayoutBoxExtent::logicalLeft(WritingMode writingMode) const
-{
-    return isHorizontalWritingMode(writingMode) ? m_left : m_top;
-}
-
-LayoutUnit LayoutBoxExtent::logicalRight(WritingMode writingMode) const
-{
-    return isHorizontalWritingMode(writingMode) ? m_right : m_bottom;
-}
-
-LayoutUnit LayoutBoxExtent::before(WritingMode writingMode) const
-{
-    switch (writingMode) {
-    case TopToBottomWritingMode:
-        return m_top;
-    case BottomToTopWritingMode:
-        return m_bottom;
-    case LeftToRightWritingMode:
-        return m_left;
-    case RightToLeftWritingMode:
-        return m_right;
-    }
-    ASSERT_NOT_REACHED();
-    return m_top;
-}
-
-LayoutUnit LayoutBoxExtent::after(WritingMode writingMode) const
-{
-    switch (writingMode) {
-    case TopToBottomWritingMode:
-        return m_bottom;
-    case BottomToTopWritingMode:
-        return m_top;
-    case LeftToRightWritingMode:
-        return m_right;
-    case RightToLeftWritingMode:
-        return m_left;
-    }
-    ASSERT_NOT_REACHED();
-    return m_bottom;
-}
-
-LayoutUnit LayoutBoxExtent::start(WritingMode writingMode, TextDirection direction) const
-{
-    if (isHorizontalWritingMode(writingMode))
-        return isLeftToRightDirection(direction) ? m_left : m_right;
-    return isLeftToRightDirection(direction) ? m_top : m_bottom;
-}
-
-LayoutUnit LayoutBoxExtent::end(WritingMode writingMode, TextDirection direction) const
-{
-    if (isHorizontalWritingMode(writingMode))
-        return isLeftToRightDirection(direction) ? m_right : m_left;
-    return isLeftToRightDirection(direction) ? m_bottom : m_top;
-}
-
-void LayoutBoxExtent::setBefore(WritingMode writingMode, LayoutUnit value)
-{
-    switch (writingMode) {
-    case TopToBottomWritingMode:
-        m_top = value;
-        break;
-    case BottomToTopWritingMode:
-        m_bottom = value;
-        break;
-    case LeftToRightWritingMode:
-        m_left = value;
-        break;
-    case RightToLeftWritingMode:
-        m_right = value;
-        break;
-    default:
-        ASSERT_NOT_REACHED();
-        m_top = value;
-    }
-}
-
-void LayoutBoxExtent::setAfter(WritingMode writingMode, LayoutUnit value)
-{
-    switch (writingMode) {
-    case TopToBottomWritingMode:
-        m_bottom = value;
-        break;
-    case BottomToTopWritingMode:
-        m_top = value;
-        break;
-    case LeftToRightWritingMode:
-        m_right = value;
-        break;
-    case RightToLeftWritingMode:
-        m_left = value;
-        break;
-    default:
-        ASSERT_NOT_REACHED();
-        m_bottom = value;
-    }
-}
-
-void LayoutBoxExtent::setStart(WritingMode writingMode, TextDirection direction, LayoutUnit value)
-{
-    if (isHorizontalWritingMode(writingMode)) {
-        if (isLeftToRightDirection(direction))
-            m_left = value;
-        else
-            m_right = value;
-    } else {
-        if (isLeftToRightDirection(direction))
-            m_top = value;
-        else
-            m_bottom = value;
-    }
-}
-
-void LayoutBoxExtent::setEnd(WritingMode writingMode, TextDirection direction, LayoutUnit value)
-{
-    if (isHorizontalWritingMode(writingMode)) {
-        if (isLeftToRightDirection(direction))
-            m_right = value;
-        else
-            m_left = value;
-    } else {
-        if (isLeftToRightDirection(direction))
-            m_bottom = value;
-        else
-            m_top = value;
-    }
-}
-
-LayoutUnit& LayoutBoxExtent::mutableLogicalLeft(WritingMode writingMode)
-{
-    return isHorizontalWritingMode(writingMode) ? m_left : m_top;
-}
-
-LayoutUnit& LayoutBoxExtent::mutableLogicalRight(WritingMode writingMode)
-{
-    return isHorizontalWritingMode(writingMode) ? m_right : m_bottom;
-}
-
-LayoutUnit& LayoutBoxExtent::mutableBefore(WritingMode writingMode)
-{
-    return isHorizontalWritingMode(writingMode) ? (isFlippedBlocksWritingMode(writingMode) ? m_bottom : m_top) :
-                                                  (isFlippedBlocksWritingMode(writingMode) ? m_right: m_left);
-}
-
-LayoutUnit& LayoutBoxExtent::mutableAfter(WritingMode writingMode)
-{
-    return isHorizontalWritingMode(writingMode) ? (isFlippedBlocksWritingMode(writingMode) ? m_top : m_bottom) :
-                                                  (isFlippedBlocksWritingMode(writingMode) ? m_left: m_right);
-}
-
-} // namespace WebCore
diff --git a/Source/WebCore/platform/graphics/LayoutBoxExtent.h b/Source/WebCore/platform/graphics/LayoutBoxExtent.h
deleted file mode 100644 (file)
index 093c4a2..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright (c) 2012, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- *     * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *     * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- *     * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef LayoutBoxExtent_h
-#define LayoutBoxExtent_h
-
-#include "LayoutUnit.h"
-#include "TextFlags.h"
-#include "WritingMode.h"
-
-namespace WebCore {
-
-class LayoutBoxExtent {
-public:
-    LayoutBoxExtent() : m_top(0), m_right(0), m_bottom(0), m_left(0) { }
-    LayoutBoxExtent(LayoutUnit top, LayoutUnit right, LayoutUnit bottom, LayoutUnit left)
-        : m_top(top), m_right(right), m_bottom(bottom), m_left(left) { }
-
-    inline LayoutUnit top() const { return m_top; }
-    inline LayoutUnit right() const { return m_right; }
-    inline LayoutUnit bottom() const { return m_bottom; }
-    inline LayoutUnit left() const { return m_left; }
-
-    inline void setTop(LayoutUnit value) { m_top = value; }
-    inline void setRight(LayoutUnit value) { m_right = value; }
-    inline void setBottom(LayoutUnit value) { m_bottom = value; }
-    inline void setLeft(LayoutUnit value) { m_left = value; }
-
-    LayoutUnit logicalTop(WritingMode) const;
-    LayoutUnit logicalBottom(WritingMode) const;
-    LayoutUnit logicalLeft(WritingMode) const;
-    LayoutUnit logicalRight(WritingMode) const;
-
-    LayoutUnit before(WritingMode) const;
-    LayoutUnit after(WritingMode) const;
-    LayoutUnit start(WritingMode, TextDirection) const;
-    LayoutUnit end(WritingMode, TextDirection) const;
-
-    void setBefore(WritingMode, LayoutUnit);
-    void setAfter(WritingMode, LayoutUnit);
-    void setStart(WritingMode, TextDirection, LayoutUnit);
-    void setEnd(WritingMode, TextDirection, LayoutUnit);
-
-    LayoutUnit& mutableLogicalLeft(WritingMode);
-    LayoutUnit& mutableLogicalRight(WritingMode);
-
-    LayoutUnit& mutableBefore(WritingMode);
-    LayoutUnit& mutableAfter(WritingMode);
-
-private:
-    LayoutUnit m_top;
-    LayoutUnit m_right;
-    LayoutUnit m_bottom;
-    LayoutUnit m_left;
-};
-
-} // namespace WebCore
-
-#endif // LayoutBoxExtent_h
index e3a5149c75309382534222ce7ca981cc150e1d23..98e3afa27b0b4f0f9e11eec8e808c3d7ebdc999f 100644 (file)
@@ -33,8 +33,8 @@
 
 #include "FloatRect.h"
 #include "IntRect.h"
-#include "LayoutBoxExtent.h"
 #include "LayoutPoint.h"
+#include "LengthBox.h"
 #include <wtf/Vector.h>
 
 namespace WebCore {
index 9e5d28c7dc208a3376d15b5e241f46cac6f10b3b..d158bb24beae75231fac2ea8da4d4a38a640543b 100644 (file)
@@ -55,6 +55,21 @@ inline bool isFlippedBlocksWritingMode(WritingMode writingMode)
     return writingMode == RightToLeftWritingMode || writingMode == BottomToTopWritingMode;
 }
 
+enum LogicalBoxSide {
+    BeforeSide,
+    EndSide,
+    AfterSide,
+    StartSide
+};
+
+enum PhysicalBoxSide {
+    NilSide = -1,
+    TopSide,
+    RightSide,
+    BottomSide,
+    LeftSide
+};
+
 } // namespace WebCore
 
 #endif // WritingMode_h
index 6fd373d4c9fa8e30e12fe0bd4a4c3edff7776b2f..41682c8e2b60cb928e461b4effaa3bf79c361c28 100644 (file)
@@ -843,10 +843,10 @@ inline void InlineFlowBox::addBorderOutsetVisualOverflow(LayoutRect& logicalVisu
 
     LayoutBoxExtent borderOutsets = lineStyle.borderImageOutsets();
 
-    LayoutUnit borderOutsetLogicalTop = borderOutsets.logicalTop(lineStyle.writingMode());
-    LayoutUnit borderOutsetLogicalBottom = borderOutsets.logicalBottom(lineStyle.writingMode());
-    LayoutUnit borderOutsetLogicalLeft = borderOutsets.logicalLeft(lineStyle.writingMode());
-    LayoutUnit borderOutsetLogicalRight = borderOutsets.logicalRight(lineStyle.writingMode());
+    LayoutUnit borderOutsetLogicalTop = borderOutsets.before(lineStyle.writingMode());
+    LayoutUnit borderOutsetLogicalBottom = borderOutsets.after(lineStyle.writingMode());
+    LayoutUnit borderOutsetLogicalLeft = borderOutsets.start(lineStyle.writingMode());
+    LayoutUnit borderOutsetLogicalRight = borderOutsets.end(lineStyle.writingMode());
 
     // Similar to how glyph overflow works, if our lines are flipped, then it's actually the opposite border that applies, since
     // the line is "upside down" in terms of block coordinates. vertical-rl and horizontal-bt are the flipped line modes.
index 267fd73481f6395996084bedfa6b6d11bde4a239..4bc1490f572482b056014b1a4a94b4cdadd7a40b 100644 (file)
@@ -262,8 +262,8 @@ public:
     void setMarginLeft(LayoutUnit margin) { m_marginBox.setLeft(margin); }
     void setMarginRight(LayoutUnit margin) { m_marginBox.setRight(margin); }
 
-    LayoutUnit marginLogicalLeft() const { return m_marginBox.logicalLeft(style().writingMode()); }
-    LayoutUnit marginLogicalRight() const { return m_marginBox.logicalRight(style().writingMode()); }
+    LayoutUnit marginLogicalLeft() const { return m_marginBox.start(style().writingMode()); }
+    LayoutUnit marginLogicalRight() const { return m_marginBox.end(style().writingMode()); }
     
     virtual LayoutUnit marginBefore(const RenderStyle* overrideStyle = nullptr) const override final { return m_marginBox.before((overrideStyle ? overrideStyle : &style())->writingMode()); }
     virtual LayoutUnit marginAfter(const RenderStyle* overrideStyle = nullptr) const override final { return m_marginBox.after((overrideStyle ? overrideStyle : &style())->writingMode()); }
@@ -277,17 +277,17 @@ public:
         const RenderStyle* styleToUse = overrideStyle ? overrideStyle : &style();
         return m_marginBox.end(styleToUse->writingMode(), styleToUse->direction());
     }
-    void setMarginBefore(LayoutUnit value, const RenderStyle* overrideStyle = nullptr) { m_marginBox.setBefore((overrideStyle ? overrideStyle : &style())->writingMode(), value); }
-    void setMarginAfter(LayoutUnit value, const RenderStyle* overrideStyle = nullptr) { m_marginBox.setAfter((overrideStyle ? overrideStyle : &style())->writingMode(), value); }
+    void setMarginBefore(LayoutUnit value, const RenderStyle* overrideStyle = nullptr) { m_marginBox.setBefore(value, (overrideStyle ? overrideStyle : &style())->writingMode()); }
+    void setMarginAfter(LayoutUnit value, const RenderStyle* overrideStyle = nullptr) { m_marginBox.setAfter(value, (overrideStyle ? overrideStyle : &style())->writingMode()); }
     void setMarginStart(LayoutUnit value, const RenderStyle* overrideStyle = nullptr)
     {
         const RenderStyle* styleToUse = overrideStyle ? overrideStyle : &style();
-        m_marginBox.setStart(styleToUse->writingMode(), styleToUse->direction(), value);
+        m_marginBox.setStart(value, styleToUse->writingMode(), styleToUse->direction());
     }
     void setMarginEnd(LayoutUnit value, const RenderStyle* overrideStyle = nullptr)
     {
         const RenderStyle* styleToUse = overrideStyle ? overrideStyle : &style();
-        m_marginBox.setEnd(styleToUse->writingMode(), styleToUse->direction(), value);
+        m_marginBox.setEnd(value, styleToUse->writingMode(), styleToUse->direction());
     }
 
     // The following five functions are used to implement collapsing margins.
index f80f2004515bcbe8ed8759fa830386f0c4bbcdf7..260d165fbfeaf17c9647355bcb212b9a876fb36b 100644 (file)
@@ -921,11 +921,13 @@ static inline LayoutSize resolveAgainstIntrinsicRatio(const LayoutSize& size, co
     return LayoutSize(size.width(), solutionHeight);
 }
 
-LayoutSize RenderBoxModelObject::calculateImageIntrinsicDimensions(StyleImage* image, const LayoutSize& positioningAreaSize, ScaleByEffectiveZoomOrNot shouldScaleOrNot) const
+bool RenderBoxModelObject::calculateImageIntrinsicDimensions(StyleImage* image, const LayoutSize& positioningAreaSize, ScaleByEffectiveZoomOrNot shouldScaleOrNot, LayoutSize& imageSize) const
 {
     // A generated image without a fixed size, will always return the container size as intrinsic size.
-    if (image->isGeneratedImage() && image->usesImageContainerSize())
-        return LayoutSize(positioningAreaSize.width(), positioningAreaSize.height());
+    if (image->isGeneratedImage() && image->usesImageContainerSize()) {
+        imageSize = LayoutSize(positioningAreaSize.width(), positioningAreaSize.height());
+        return true;
+    }
 
     Length intrinsicWidth;
     Length intrinsicHeight;
@@ -935,31 +937,36 @@ LayoutSize RenderBoxModelObject::calculateImageIntrinsicDimensions(StyleImage* i
     ASSERT(!intrinsicWidth.isPercentOrCalculated());
     ASSERT(!intrinsicHeight.isPercentOrCalculated());
 
-    LayoutSize resolvedSize(intrinsicWidth.value(), intrinsicHeight.value());
-    LayoutSize minimumSize(resolvedSize.width() > 0 ? 1 : 0, resolvedSize.height() > 0 ? 1 : 0);
+    imageSize = LayoutSize(intrinsicWidth.value(), intrinsicHeight.value());
+    LayoutSize minimumSize(imageSize.width() > 0 ? 1 : 0, imageSize.height() > 0 ? 1 : 0);
     if (shouldScaleOrNot == ScaleByEffectiveZoom)
-        resolvedSize.scale(style().effectiveZoom());
-    resolvedSize.clampToMinimumSize(minimumSize);
+        imageSize.scale(style().effectiveZoom());
+    imageSize.clampToMinimumSize(minimumSize);
 
-    if (!resolvedSize.isEmpty())
-        return resolvedSize;
+    if (!imageSize.isEmpty())
+        return true;
 
     // If the image has one of either an intrinsic width or an intrinsic height:
     // * and an intrinsic aspect ratio, then the missing dimension is calculated from the given dimension and the ratio.
     // * and no intrinsic aspect ratio, then the missing dimension is assumed to be the size of the rectangle that
     //   establishes the coordinate system for the 'background-position' property.
-    if (resolvedSize.width() > 0 || resolvedSize.height() > 0)
-        return resolveAgainstIntrinsicWidthOrHeightAndRatio(positioningAreaSize, intrinsicRatio, resolvedSize.width(), resolvedSize.height());
+    if (imageSize.width() > 0 || imageSize.height() > 0) {
+        imageSize = resolveAgainstIntrinsicWidthOrHeightAndRatio(positioningAreaSize, intrinsicRatio, imageSize.width(), imageSize.height());
+        return true;
+    }
 
     // If the image has no intrinsic dimensions and has an intrinsic ratio the dimensions must be assumed to be the
     // largest dimensions at that ratio such that neither dimension exceeds the dimensions of the rectangle that
     // establishes the coordinate system for the 'background-position' property.
-    if (!intrinsicRatio.isEmpty())
-        return resolveAgainstIntrinsicRatio(positioningAreaSize, intrinsicRatio);
+    if (!intrinsicRatio.isEmpty()) {
+        imageSize = resolveAgainstIntrinsicRatio(positioningAreaSize, intrinsicRatio);
+        return false;
+    }
 
     // If the image has no intrinsic ratio either, then the dimensions must be assumed to be the rectangle that
     // establishes the coordinate system for the 'background-position' property.
-    return positioningAreaSize;
+    imageSize = positioningAreaSize;
+    return false;
 }
 
 LayoutSize RenderBoxModelObject::calculateFillTileSize(const FillLayer& fillLayer, const LayoutSize& positioningAreaSize) const
@@ -969,7 +976,7 @@ LayoutSize RenderBoxModelObject::calculateFillTileSize(const FillLayer& fillLaye
 
     LayoutSize imageIntrinsicSize;
     if (image) {
-        imageIntrinsicSize = calculateImageIntrinsicDimensions(image, positioningAreaSize, ScaleByEffectiveZoom);
+        calculateImageIntrinsicDimensions(image, positioningAreaSize, ScaleByEffectiveZoom, imageIntrinsicSize);
         imageIntrinsicSize.scale(1 / image->imageScaleFactor(), 1 / image->imageScaleFactor());
     } else
         imageIntrinsicSize = positioningAreaSize;
@@ -1238,15 +1245,6 @@ void RenderBoxModelObject::getGeometryForBackgroundImage(const RenderLayerModelO
     destRect = geometry.destRect();
 }
 
-static LayoutUnit computeBorderImageSide(Length borderSlice, LayoutUnit borderSide, LayoutUnit imageSide, LayoutUnit boxExtent)
-{
-    if (borderSlice.isRelative())
-        return borderSlice.value() * borderSide;
-    if (borderSlice.isAuto())
-        return imageSide;
-    return valueForLength(borderSlice, boxExtent);
-}
-
 bool RenderBoxModelObject::paintNinePieceImage(GraphicsContext* graphicsContext, const LayoutRect& rect, const RenderStyle& style,
                                                const NinePieceImage& ninePieceImage, CompositeOperator op)
 {
@@ -1263,152 +1261,18 @@ bool RenderBoxModelObject::paintNinePieceImage(GraphicsContext* graphicsContext,
     // FIXME: border-image is broken with full page zooming when tiling has to happen, since the tiling function
     // doesn't have any understanding of the zoom that is in effect on the tile.
     float deviceScaleFactor = document().deviceScaleFactor();
+
     LayoutRect rectWithOutsets = rect;
     rectWithOutsets.expand(style.imageOutsets(ninePieceImage));
-    LayoutRect borderImageRect = LayoutRect(snapRectToDevicePixels(rectWithOutsets, deviceScaleFactor));
+    LayoutRect destination = LayoutRect(snapRectToDevicePixels(rectWithOutsets, deviceScaleFactor));
 
-    LayoutSize imageSize = calculateImageIntrinsicDimensions(styleImage, borderImageRect.size(), DoNotScaleByEffectiveZoom);
+    LayoutSize source;
+    bool intrinsicSource = calculateImageIntrinsicDimensions(styleImage, destination.size(), DoNotScaleByEffectiveZoom, source);
 
     // If both values are ‘auto’ then the intrinsic width and/or height of the image should be used, if any.
-    styleImage->setContainerSizeForRenderer(this, imageSize, style.effectiveZoom());
-
-    LayoutUnit imageWidth = imageSize.width();
-    LayoutUnit imageHeight = imageSize.height();
-
-    float imageScaleFactor = styleImage->imageScaleFactor();
-    LayoutUnit topSlice = std::min<LayoutUnit>(imageHeight, valueForLength(ninePieceImage.imageSlices().top(), imageHeight)) * imageScaleFactor;
-    LayoutUnit rightSlice = std::min<LayoutUnit>(imageWidth, valueForLength(ninePieceImage.imageSlices().right(), imageWidth)) * imageScaleFactor;
-    LayoutUnit bottomSlice = std::min<LayoutUnit>(imageHeight, valueForLength(ninePieceImage.imageSlices().bottom(), imageHeight)) * imageScaleFactor;
-    LayoutUnit leftSlice = std::min<LayoutUnit>(imageWidth, valueForLength(ninePieceImage.imageSlices().left(), imageWidth)) * imageScaleFactor;
-
-    ENinePieceImageRule hRule = ninePieceImage.horizontalRule();
-    ENinePieceImageRule vRule = ninePieceImage.verticalRule();
-
-    LayoutUnit topWidth = computeBorderImageSide(ninePieceImage.borderSlices().top(), style.borderTopWidth(), topSlice, borderImageRect.height());
-    LayoutUnit rightWidth = computeBorderImageSide(ninePieceImage.borderSlices().right(), style.borderRightWidth(), rightSlice, borderImageRect.width());
-    LayoutUnit bottomWidth = computeBorderImageSide(ninePieceImage.borderSlices().bottom(), style.borderBottomWidth(), bottomSlice, borderImageRect.height());
-    LayoutUnit leftWidth = computeBorderImageSide(ninePieceImage.borderSlices().left(), style.borderLeftWidth(), leftSlice, borderImageRect.width());
-
-    // Reduce the widths if they're too large.
-    // The spec says: Given Lwidth as the width of the border image area, Lheight as its height, and Wside as the border image width
-    // offset for the side, let f = min(Lwidth/(Wleft+Wright), Lheight/(Wtop+Wbottom)). If f < 1, then all W are reduced by
-    // multiplying them by f.
-    LayoutUnit borderSideWidth = std::max<LayoutUnit>(1 / deviceScaleFactor, leftWidth + rightWidth);
-    LayoutUnit borderSideHeight = std::max<LayoutUnit>(1 / deviceScaleFactor, topWidth + bottomWidth);
-    float borderSideScaleFactor = std::min((float)borderImageRect.width() / borderSideWidth, (float)borderImageRect.height() / borderSideHeight);
-    if (borderSideScaleFactor < 1) {
-        topWidth *= borderSideScaleFactor;
-        rightWidth *= borderSideScaleFactor;
-        bottomWidth *= borderSideScaleFactor;
-        leftWidth *= borderSideScaleFactor;
-    }
-
-    bool drawLeft = leftSlice > 0 && leftWidth > 0;
-    bool drawTop = topSlice > 0 && topWidth > 0;
-    bool drawRight = rightSlice > 0 && rightWidth > 0;
-    bool drawBottom = bottomSlice > 0 && bottomWidth > 0;
-    bool drawMiddle = ninePieceImage.fill() && (imageWidth - leftSlice - rightSlice) > 0 && (borderImageRect.width() - leftWidth - rightWidth) > 0
-                      && (imageHeight - topSlice - bottomSlice) > 0 && (borderImageRect.height() - topWidth - bottomWidth) > 0;
-
-    RefPtr<Image> image = styleImage->image(this, imageSize);
-    ColorSpace colorSpace = style.colorSpace();
-    
-    float destinationWidth = borderImageRect.width() - leftWidth - rightWidth;
-    float destinationHeight = borderImageRect.height() - topWidth - bottomWidth;
-    
-    float sourceWidth = imageWidth - leftSlice - rightSlice;
-    float sourceHeight = imageHeight - topSlice - bottomSlice;
-    
-    float leftSideScale = drawLeft ? (float)leftWidth / leftSlice : 1;
-    float rightSideScale = drawRight ? (float)rightWidth / rightSlice : 1;
-    float topSideScale = drawTop ? (float)topWidth / topSlice : 1;
-    float bottomSideScale = drawBottom ? (float)bottomWidth / bottomSlice : 1;
-
-    float x = borderImageRect.location().x();
-    float y = borderImageRect.location().y();
-    if (drawLeft) {
-        // Paint the top and bottom left corners.
-
-        // The top left corner rect is (tx, ty, leftWidth, topWidth)
-        // The rect to use from within the image is obtained from our slice, and is (0, 0, leftSlice, topSlice)
-        if (drawTop)
-            graphicsContext->drawImage(image.get(), colorSpace, snapRectToDevicePixels(x, y, leftWidth, topWidth, deviceScaleFactor),
-                snapRectToDevicePixels(0, 0, leftSlice, topSlice, deviceScaleFactor), op);
-
-        // The bottom left corner rect is (tx, ty + h - bottomWidth, leftWidth, bottomWidth)
-        // The rect to use from within the image is (0, imageHeight - bottomSlice, leftSlice, botomSlice)
-        if (drawBottom)
-            graphicsContext->drawImage(image.get(), colorSpace, snapRectToDevicePixels(x, borderImageRect.maxY() - bottomWidth, leftWidth, bottomWidth, deviceScaleFactor),
-                snapRectToDevicePixels(0, imageHeight - bottomSlice, leftSlice, bottomSlice, deviceScaleFactor), op);
-
-        // Paint the left edge.
-        // Have to scale and tile into the border rect.
-        if (sourceHeight > 0)
-            graphicsContext->drawTiledImage(image.get(), colorSpace, snapRectToDevicePixels(x, y + topWidth, leftWidth, destinationHeight, deviceScaleFactor),
-                snapRectToDevicePixels(0, topSlice, leftSlice, sourceHeight, deviceScaleFactor), FloatSize(leftSideScale, leftSideScale), Image::StretchTile, (Image::TileRule)vRule, op);
-    }
-
-    if (drawRight) {
-        // Paint the top and bottom right corners
-        // The top right corner rect is (tx + w - rightWidth, ty, rightWidth, topWidth)
-        // The rect to use from within the image is obtained from our slice, and is (imageWidth - rightSlice, 0, rightSlice, topSlice)
-        if (drawTop)
-            graphicsContext->drawImage(image.get(), colorSpace, snapRectToDevicePixels(borderImageRect.maxX() - rightWidth, y, rightWidth, topWidth, deviceScaleFactor),
-                snapRectToDevicePixels(imageWidth - rightSlice, 0, rightSlice, topSlice, deviceScaleFactor), op);
-
-        // The bottom right corner rect is (tx + w - rightWidth, ty + h - bottomWidth, rightWidth, bottomWidth)
-        // The rect to use from within the image is (imageWidth - rightSlice, imageHeight - bottomSlice, rightSlice, bottomSlice)
-        if (drawBottom)
-            graphicsContext->drawImage(image.get(), colorSpace, snapRectToDevicePixels(borderImageRect.maxX() - rightWidth, borderImageRect.maxY() - bottomWidth,
-                rightWidth, bottomWidth, deviceScaleFactor), snapRectToDevicePixels(imageWidth - rightSlice, imageHeight - bottomSlice, rightSlice, bottomSlice, deviceScaleFactor),
-                op);
-
-        // Paint the right edge.
-        if (sourceHeight > 0)
-            graphicsContext->drawTiledImage(image.get(), colorSpace, snapRectToDevicePixels(borderImageRect.maxX() - rightWidth, y + topWidth, rightWidth, destinationHeight, deviceScaleFactor),
-                snapRectToDevicePixels(imageWidth - rightSlice, topSlice, rightSlice, sourceHeight, deviceScaleFactor), FloatSize(rightSideScale, rightSideScale),
-                Image::StretchTile, (Image::TileRule)vRule, op);
-    }
-
-    // Paint the top edge.
-    if (drawTop && sourceWidth > 0)
-        graphicsContext->drawTiledImage(image.get(), colorSpace, snapRectToDevicePixels(x + leftWidth, y, destinationWidth, topWidth, deviceScaleFactor),
-            snapRectToDevicePixels(leftSlice, 0, sourceWidth, topSlice, deviceScaleFactor), FloatSize(topSideScale, topSideScale), (Image::TileRule)hRule, Image::StretchTile, op);
-
-    // Paint the bottom edge.
-    if (drawBottom && sourceWidth > 0)
-        graphicsContext->drawTiledImage(image.get(), colorSpace, snapRectToDevicePixels(x + leftWidth, borderImageRect.maxY() - bottomWidth, destinationWidth, bottomWidth, deviceScaleFactor),
-            snapRectToDevicePixels(leftSlice, imageHeight - bottomSlice, sourceWidth, bottomSlice, deviceScaleFactor), FloatSize(bottomSideScale, bottomSideScale),
-            (Image::TileRule)hRule, Image::StretchTile, op);
-
-    // Paint the middle.
-    if (drawMiddle) {
-        FloatSize middleScaleFactor(1, 1);
-        if (drawTop)
-            middleScaleFactor.setWidth(topSideScale);
-        else if (drawBottom)
-            middleScaleFactor.setWidth(bottomSideScale);
-        if (drawLeft)
-            middleScaleFactor.setHeight(leftSideScale);
-        else if (drawRight)
-            middleScaleFactor.setHeight(rightSideScale);
-            
-        // For "stretch" rules, just override the scale factor and replace. We only had to do this for the
-        // center tile, since sides don't even use the scale factor unless they have a rule other than "stretch".
-        // The middle however can have "stretch" specified in one axis but not the other, so we have to
-        // correct the scale here.
-        if (hRule == StretchImageRule)
-            middleScaleFactor.setWidth(destinationWidth / sourceWidth);
-            
-        if (vRule == StretchImageRule)
-            middleScaleFactor.setHeight(destinationHeight / sourceHeight);
-        
-        graphicsContext->drawTiledImage(image.get(), colorSpace,
-            snapRectToDevicePixels(x + leftWidth, y + topWidth, destinationWidth, destinationHeight, deviceScaleFactor),
-            snapRectToDevicePixels(leftSlice, topSlice, sourceWidth, sourceHeight, deviceScaleFactor),
-            middleScaleFactor, (Image::TileRule)hRule, (Image::TileRule)vRule, op);
-    }
+    styleImage->setContainerSizeForRenderer(this, source, style.effectiveZoom());
 
+    ninePieceImage.paint(graphicsContext, this, style, destination, source, intrinsicSource, deviceScaleFactor, op);
     return true;
 }
 
index b4f46c7406b09b6b221590239292d6267acadb9e..ae1572f666caffffd09b4d50cc0d8db018b7151b 100644 (file)
@@ -289,7 +289,7 @@ public:
     void moveChildrenTo(RenderBoxModelObject* toBoxModelObject, RenderObject* startChild, RenderObject* endChild, RenderObject* beforeChild, bool fullRemoveInsert = false);
 
     enum ScaleByEffectiveZoomOrNot { ScaleByEffectiveZoom, DoNotScaleByEffectiveZoom };
-    LayoutSize calculateImageIntrinsicDimensions(StyleImage*, const LayoutSize& scaledPositioningAreaSize, ScaleByEffectiveZoomOrNot) const;
+    bool calculateImageIntrinsicDimensions(StyleImage*, const LayoutSize& scaledPositioningAreaSize, ScaleByEffectiveZoomOrNot, LayoutSize& imageSize) const;
 
 private:
     LayoutUnit computedCSSPadding(const Length&) const;
index 3063e8c63a6de15140d6b249136cc6cb0c71b200..900c8700386367bbd020d538d0b76ce569705d14 100644 (file)
@@ -1426,7 +1426,8 @@ void RenderListMarker::updateContent()
         // until we support the CSS3 marker pseudoclass to allow control over the width and height of the marker box.
         LayoutUnit bulletWidth = style().fontMetrics().ascent() / LayoutUnit(2);
         LayoutSize defaultBulletSize(bulletWidth, bulletWidth);
-        LayoutSize imageSize = calculateImageIntrinsicDimensions(m_image.get(), defaultBulletSize, DoNotScaleByEffectiveZoom);
+        LayoutSize imageSize;
+        calculateImageIntrinsicDimensions(m_image.get(), defaultBulletSize, DoNotScaleByEffectiveZoom, imageSize);
         m_image->setContainerSizeForRenderer(this, imageSize, style().effectiveZoom());
         return;
     }
index 96ad5d016e1f41ee0391c4878c644759f3cf2777..f29c3a8c111e5a98f823cf8cde322a9dddb5ecf2 100644 (file)
@@ -148,7 +148,8 @@ static LayoutRect getShapeImageMarginRect(const RenderBox& renderBox, const Layo
 
 std::unique_ptr<Shape> ShapeOutsideInfo::createShapeForImage(StyleImage* styleImage, float shapeImageThreshold, WritingMode writingMode, float margin) const
 {
-    const LayoutSize& imageSize = m_renderer.calculateImageIntrinsicDimensions(styleImage, m_referenceBoxLogicalSize, RenderImage::ScaleByEffectiveZoom);
+    LayoutSize imageSize;
+    m_renderer.calculateImageIntrinsicDimensions(styleImage, m_referenceBoxLogicalSize, RenderImage::ScaleByEffectiveZoom, imageSize);
     styleImage->setContainerSizeForRenderer(&m_renderer, imageSize, m_renderer.style().effectiveZoom());
 
     const LayoutRect& marginRect = getShapeImageMarginRect(m_renderer, m_referenceBoxLogicalSize);
index 971074efb721da8a8162d1d6d1bc2dd1bce76048..cd1a5834c224cfa7ed7204740719f8fa54f99618 100644 (file)
@@ -92,6 +92,11 @@ public:
             return 0;
         return m_bottom.width();
     }
+
+    FloatBoxExtent borderWidth() const
+    {
+        return FloatBoxExtent(borderTopWidth(), borderRightWidth(), borderBottomWidth(), borderLeftWidth());
+    }
     
     bool operator==(const BorderData& o) const
     {
index 57ecd12d25f123906f5aaedf6193a24c341fd9cc..2744ce1bd4015c0848ef69840d1c17e0deacd50c 100644 (file)
@@ -2,7 +2,7 @@
  * Copyright (C) 2000 Lars Knoll (knoll@kde.org)
  *           (C) 2000 Antti Koivisto (koivisto@kde.org)
  *           (C) 2000 Dirk Mueller (mueller@kde.org)
- * Copyright (C) 2003, 2005, 2006, 2007, 2008, 2013 Apple Inc. All rights reserved.
+ * Copyright (C) 2003, 2005, 2006, 2007, 2008, 2013, 2015 Apple Inc. All rights reserved.
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Library General Public
 
 #include "config.h"
 #include "NinePieceImage.h"
+
+#include "GraphicsContext.h"
+#include "LengthFunctions.h"
+#include "RenderStyle.h"
 #include <wtf/NeverDestroyed.h>
 
 namespace WebCore {
@@ -50,11 +54,205 @@ NinePieceImage::NinePieceImage(PassRefPtr<StyleImage> image, LengthBox imageSlic
     m_data.access()->verticalRule = verticalRule;
 }
 
+LayoutUnit NinePieceImage::computeSlice(Length length, LayoutUnit width, LayoutUnit slice, LayoutUnit extent)
+{
+    if (length.isRelative())
+        return length.value() * width;
+    if (length.isAuto())
+        return slice;
+    return valueForLength(length, extent);
+}
+
+LayoutBoxExtent NinePieceImage::computeSlices(const LayoutSize& size, const LengthBox& lengths, int scaleFactor)
+{
+    LayoutUnit top    = std::min<LayoutUnit>(size.height(), valueForLength(lengths.top(),    size.height())) * scaleFactor;
+    LayoutUnit right  = std::min<LayoutUnit>(size.width(),  valueForLength(lengths.right(),  size.width()))  * scaleFactor;
+    LayoutUnit bottom = std::min<LayoutUnit>(size.height(), valueForLength(lengths.bottom(), size.height())) * scaleFactor;
+    LayoutUnit left   = std::min<LayoutUnit>(size.width(),  valueForLength(lengths.left(),   size.width()))  * scaleFactor;
+    return LayoutBoxExtent(top, right, bottom, left);
+}
+
+LayoutBoxExtent NinePieceImage::computeSlices(const LayoutSize& size, const LengthBox& lengths, const FloatBoxExtent& widths, const LayoutBoxExtent& slices)
+{
+    LayoutUnit top    = computeSlice(lengths.top(),    widths.top(),    slices.top(),    size.height());
+    LayoutUnit right  = computeSlice(lengths.right(),  widths.right(),  slices.right(),  size.width());
+    LayoutUnit bottom = computeSlice(lengths.bottom(), widths.bottom(), slices.bottom(), size.height());
+    LayoutUnit left   = computeSlice(lengths.left(),   widths.left(),   slices.left(),   size.width());
+    return LayoutBoxExtent(top, right, bottom, left);
+}
+
+void NinePieceImage::scaleSlicesIfNeeded(const LayoutSize& size, LayoutBoxExtent& slices, int scaleFactor)
+{
+    LayoutUnit width  = std::max<LayoutUnit>(1 / scaleFactor, slices.left() + slices.right());
+    LayoutUnit height = std::max<LayoutUnit>(1 / scaleFactor, slices.top() + slices.bottom());
+
+    float sliceScaleFactor = std::min((float)size.width() / width, (float)size.height() / height);
+
+    if (sliceScaleFactor >= 1)
+        return;
+
+    // All slices are reduced by multiplying them by sliceScaleFactor.
+    slices.top()    *= sliceScaleFactor;
+    slices.right()  *= sliceScaleFactor;
+    slices.bottom() *= sliceScaleFactor;
+    slices.left()   *= sliceScaleFactor;
+}
+
+bool NinePieceImage::isEmptyPieceRect(ImagePiece piece, const LayoutBoxExtent& slices)
+{
+    if (piece == MiddlePiece)
+        return false;
+
+    PhysicalBoxSide horizontalSide = imagePieceHorizontalSide(piece);
+    PhysicalBoxSide verticalSide = imagePieceVerticalSide(piece);
+    return !((horizontalSide == NilSide || slices.at(horizontalSide)) && (verticalSide == NilSide || slices.at(verticalSide)));
+}
+
+bool NinePieceImage::isEmptyPieceRect(ImagePiece piece, const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects)
+{
+    return destinationRects[piece].isEmpty() || sourceRects[piece].isEmpty();
+}
+
+Vector<FloatRect> NinePieceImage::computeIntrinsicRects(const FloatRect& outer, const LayoutBoxExtent& slices, float deviceScaleFactor)
+{
+    FloatRect inner = outer;
+    inner.move(slices.left(), slices.top());
+    inner.contract(slices.left() + slices.right(), slices.top() + slices.bottom());
+    ASSERT(outer.contains(inner));
+
+    Vector<FloatRect> rects(MaxPiece);
+
+    rects[TopLeftPiece]     = snapRectToDevicePixels(outer.x(),    outer.y(),    slices.left(),  slices.top(),    deviceScaleFactor);
+    rects[BottomLeftPiece]  = snapRectToDevicePixels(outer.x(),    inner.maxY(), slices.left(),  slices.bottom(), deviceScaleFactor);
+    rects[LeftPiece]        = snapRectToDevicePixels(outer.x(),    inner.y(),    slices.left(),  inner.height(),  deviceScaleFactor);
+
+    rects[TopRightPiece]    = snapRectToDevicePixels(inner.maxX(), outer.y(),    slices.right(), slices.top(),    deviceScaleFactor);
+    rects[BottomRightPiece] = snapRectToDevicePixels(inner.maxX(), inner.maxY(), slices.right(), slices.bottom(), deviceScaleFactor);
+    rects[RightPiece]       = snapRectToDevicePixels(inner.maxX(), inner.y(),    slices.right(), inner.height(),  deviceScaleFactor);
+
+    rects[TopPiece]         = snapRectToDevicePixels(inner.x(),    outer.y(),    inner.width(),  slices.top(),    deviceScaleFactor);
+    rects[BottomPiece]      = snapRectToDevicePixels(inner.x(),    inner.maxY(), inner.width(),  slices.bottom(), deviceScaleFactor);
+
+    rects[MiddlePiece]      = snapRectToDevicePixels(inner.x(),    inner.y(),    inner.width(),  inner.height(),  deviceScaleFactor);
+    return rects;
+}
+
+Vector<FloatRect> NinePieceImage::computeNonIntrinsicRects(const Vector<FloatRect>& intrinsicRects, const LayoutBoxExtent& slices)
+{
+    Vector<FloatRect> rects(MaxPiece);
+
+    for (ImagePiece piece = MinPiece; piece < MaxPiece; ++piece) {
+        if (isEmptyPieceRect(piece, slices))
+            continue;
+        rects[piece] = FloatRect(FloatPoint(), intrinsicRects[piece].size());
+    }
+
+    return rects;
+}
+
+FloatSize NinePieceImage::computeIntrinsicSideTileScale(ImagePiece piece, const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects)
+{
+    ASSERT(!isCornerPiece(piece) && !isMiddlePiece(piece));
+    if (isEmptyPieceRect(piece, destinationRects, sourceRects))
+        return FloatSize(1, 1);
+
+    float scale;
+    if (isVerticalPiece(piece))
+        scale = destinationRects[piece].height() / sourceRects[piece].height();
+    else
+        scale = destinationRects[piece].width() / sourceRects[piece].width();
+
+    return FloatSize(scale, scale);
+}
+
+FloatSize NinePieceImage::computeIntrinsicMiddleTileScale(const Vector<FloatSize>& scales, const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects, ENinePieceImageRule hRule, ENinePieceImageRule vRule)
+{
+    FloatSize scale(1, 1);
+    if (isEmptyPieceRect(MiddlePiece, destinationRects, sourceRects))
+        return scale;
+
+    // Unlike the side pieces, the middle piece can have "stretch" specified in one axis but not the other.
+    // In fact the side pieces don't even use the scale factor unless they have a rule other than "stretch".
+    if (hRule == StretchImageRule)
+        scale.setWidth(destinationRects[MiddlePiece].width() / sourceRects[MiddlePiece].width());
+    else if (!isEmptyPieceRect(TopPiece, destinationRects, sourceRects))
+        scale.setWidth(scales[TopPiece].width());
+    else if (!isEmptyPieceRect(BottomPiece, destinationRects, sourceRects))
+        scale.setWidth(scales[BottomPiece].width());
+
+    if (vRule == StretchImageRule)
+        scale.setHeight(destinationRects[MiddlePiece].height() / sourceRects[MiddlePiece].height());
+    else if (!isEmptyPieceRect(LeftPiece, destinationRects, sourceRects))
+        scale.setHeight(scales[LeftPiece].height());
+    else if (!isEmptyPieceRect(RightPiece, destinationRects, sourceRects))
+        scale.setHeight(scales[RightPiece].height());
+
+    return scale;
+}
+
+Vector<FloatSize> NinePieceImage::computeIntrinsicTileScales(const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects, ENinePieceImageRule hRule, ENinePieceImageRule vRule)
+{
+    Vector<FloatSize> scales(MaxPiece, FloatSize(1, 1));
+
+    scales[TopPiece]    = computeIntrinsicSideTileScale(TopPiece,    destinationRects, sourceRects);
+    scales[RightPiece]  = computeIntrinsicSideTileScale(RightPiece,  destinationRects, sourceRects);
+    scales[BottomPiece] = computeIntrinsicSideTileScale(BottomPiece, destinationRects, sourceRects);
+    scales[LeftPiece]   = computeIntrinsicSideTileScale(LeftPiece,   destinationRects, sourceRects);
+
+    scales[MiddlePiece] = computeIntrinsicMiddleTileScale(scales, destinationRects, sourceRects, hRule, vRule);
+    return scales;
+}
+
+Vector<FloatSize> NinePieceImage::computeNonIntrinsicTileScales()
+{
+    return Vector<FloatSize>(MaxPiece, FloatSize(1, 1));
+}
+
+void NinePieceImage::paint(GraphicsContext* graphicsContext, RenderElement* renderer, const RenderStyle& style, const LayoutRect& destination, const LayoutSize& source,  bool intrinsicSource, float deviceScaleFactor, CompositeOperator op) const
+{
+    StyleImage* styleImage = image();
+    ASSERT(styleImage && styleImage->isLoaded());
+
+    LayoutBoxExtent sourceSlices = computeSlices(source, imageSlices(), styleImage->imageScaleFactor());
+    LayoutBoxExtent destinationSlices = computeSlices(destination.size(), borderSlices(), style.borderWidth(), sourceSlices);
+
+    scaleSlicesIfNeeded(destination.size(), destinationSlices, deviceScaleFactor);
+
+    Vector<FloatRect> destinationRects = computeIntrinsicRects(destination, destinationSlices, deviceScaleFactor);
+    Vector<FloatRect> sourceRects;
+    Vector<FloatSize> tileScales;
+
+    if (intrinsicSource) {
+        sourceRects = computeIntrinsicRects(FloatRect(FloatPoint(), source), sourceSlices, deviceScaleFactor);
+        tileScales = computeIntrinsicTileScales(destinationRects, sourceRects, horizontalRule(), verticalRule());
+    } else {
+        sourceRects = computeNonIntrinsicRects(destinationRects, sourceSlices);
+        tileScales = computeNonIntrinsicTileScales();
+    }
+
+    RefPtr<Image> image = styleImage->image(renderer, source);
+    ColorSpace colorSpace = style.colorSpace();
+
+    for (ImagePiece piece = MinPiece; piece < MaxPiece; ++piece) {
+        if ((piece == MiddlePiece && !fill()) || isEmptyPieceRect(piece, destinationRects, sourceRects))
+            continue;
+
+        if (isCornerPiece(piece)) {
+            graphicsContext->drawImage(image.get(), colorSpace, destinationRects[piece], sourceRects[piece], op);
+            continue;
+        }
+
+        Image::TileRule hRule = isHorizontalPiece(piece) ? static_cast<Image::TileRule>(horizontalRule()) : Image::StretchTile;
+        Image::TileRule vRule = isVerticalPiece(piece) ? static_cast<Image::TileRule>(verticalRule()) : Image::StretchTile;
+        graphicsContext->drawTiledImage(image.get(), colorSpace, destinationRects[piece], sourceRects[piece], tileScales[piece], hRule, vRule, op);
+    }
+}
+
 NinePieceImageData::NinePieceImageData()
     : fill(false)
     , horizontalRule(StretchImageRule)
     , verticalRule(StretchImageRule)
-    , image(0)
+    , image(nullptr)
     , imageSlices(Length(100, Percent), Length(100, Percent), Length(100, Percent), Length(100, Percent))
     , borderSlices(Length(1, Relative), Length(1, Relative), Length(1, Relative), Length(1, Relative))
     , outset(0)
index 5bab364217f9fbc4244a53a3c3a59637d3b0e612..d220df05932c78f02aab1d3118034e1366f11ca9 100644 (file)
@@ -2,7 +2,7 @@
  * Copyright (C) 2000 Lars Knoll (knoll@kde.org)
  *           (C) 2000 Antti Koivisto (koivisto@kde.org)
  *           (C) 2000 Dirk Mueller (mueller@kde.org)
- * Copyright (C) 2003, 2005, 2006, 2007, 2008, 2013 Apple Inc. All rights reserved.
+ * Copyright (C) 2003, 2005, 2006, 2007, 2008, 2013, 2015 Apple Inc. All rights reserved.
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Library General Public
 #define NinePieceImage_h
 
 #include "DataRef.h"
+#include "LayoutRect.h"
+#include "LayoutSize.h"
 #include "LayoutUnit.h"
 #include "LengthBox.h"
 #include "StyleImage.h"
+#include <wtf/Vector.h>
 
 namespace WebCore {
 
@@ -35,6 +38,70 @@ enum ENinePieceImageRule {
     StretchImageRule, RoundImageRule, SpaceImageRule, RepeatImageRule
 };
 
+enum ImagePiece {
+    MinPiece = 0,
+    TopLeftPiece = MinPiece,
+    LeftPiece,
+    BottomLeftPiece,
+    TopRightPiece,
+    RightPiece,
+    BottomRightPiece,
+    TopPiece,
+    BottomPiece,
+    MiddlePiece,
+    MaxPiece
+};
+
+inline ImagePiece& operator++(ImagePiece& piece)
+{
+    piece = static_cast<ImagePiece>(static_cast<int>(piece) + 1);
+    return piece;
+}
+
+inline bool isCornerPiece(ImagePiece piece)
+{
+    return piece == TopLeftPiece || piece == TopRightPiece || piece == BottomLeftPiece || piece == BottomRightPiece;
+}
+
+inline bool isMiddlePiece(ImagePiece piece)
+{
+    return piece == MiddlePiece;
+}
+
+inline bool isHorizontalPiece(ImagePiece piece)
+{
+    return piece == TopPiece || piece == BottomPiece || piece == MiddlePiece;
+}
+
+inline bool isVerticalPiece(ImagePiece piece)
+{
+    return piece == LeftPiece || piece == RightPiece || piece == MiddlePiece;
+}
+
+inline PhysicalBoxSide imagePieceHorizontalSide(ImagePiece piece)
+{
+    if (piece == TopLeftPiece || piece == TopPiece || piece == TopRightPiece)
+        return TopSide;
+
+    if (piece == BottomLeftPiece || piece == BottomPiece || piece == BottomRightPiece)
+        return BottomSide;
+
+    return NilSide;
+}
+
+inline PhysicalBoxSide imagePieceVerticalSide(ImagePiece piece)
+{
+    if (piece == TopLeftPiece || piece == LeftPiece || piece == BottomLeftPiece)
+        return LeftSide;
+
+    if (piece == TopRightPiece || piece == RightPiece || piece == BottomRightPiece)
+        return RightSide;
+
+    return NilSide;
+}
+
+class RenderStyle;
+
 class NinePieceImageData : public RefCounted<NinePieceImageData> {
 public:
     static Ref<NinePieceImageData> create() { return adoptRef(*new NinePieceImageData); }
@@ -122,6 +189,25 @@ public:
         return outsetSide.value();
     }
 
+    static LayoutUnit computeSlice(Length, LayoutUnit width, LayoutUnit slice, LayoutUnit extent);
+    static LayoutBoxExtent computeSlices(const LayoutSize&, const LengthBox& lengths, int scaleFactor);
+    static LayoutBoxExtent computeSlices(const LayoutSize&, const LengthBox& lengths, const FloatBoxExtent& widths, const LayoutBoxExtent& slices);
+
+    static bool isEmptyPieceRect(ImagePiece, const LayoutBoxExtent& slices);
+    static bool isEmptyPieceRect(ImagePiece, const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects);
+
+    static Vector<FloatRect> computeIntrinsicRects(const FloatRect& outer, const LayoutBoxExtent& slices, float deviceScaleFactor);
+    static Vector<FloatRect> computeNonIntrinsicRects(const Vector<FloatRect>& intrinsicRects, const LayoutBoxExtent& slices);
+
+    static void scaleSlicesIfNeeded(const LayoutSize&, LayoutBoxExtent& slices, int scaleFactor);
+
+    static FloatSize computeIntrinsicSideTileScale(ImagePiece, const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects);
+    static FloatSize computeIntrinsicMiddleTileScale(const Vector<FloatSize>& scales, const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects, ENinePieceImageRule hRule, ENinePieceImageRule vRule);
+    static Vector<FloatSize> computeIntrinsicTileScales(const Vector<FloatRect>& destinationRects, const Vector<FloatRect>& sourceRects, ENinePieceImageRule hRule, ENinePieceImageRule vRule);
+    static Vector<FloatSize> computeNonIntrinsicTileScales();
+
+    void paint(GraphicsContext*, RenderElement*, const RenderStyle&, const LayoutRect& destination, const LayoutSize& source, bool intrinsicSource, float deviceScaleFactor, CompositeOperator) const;
+
 private:
     DataRef<NinePieceImageData> m_data;
 };
index 270cfba4ae9d71497859f1440e7e786f7aa46d08..87c58e9bfc7f44e4f2b9c26f1ef59d68f1209fdc 100644 (file)
@@ -921,10 +921,10 @@ void RenderStyle::setMaskImage(const Vector<RefPtr<MaskImageOperation>>& ops)
 void RenderStyle::setClip(Length top, Length right, Length bottom, Length left)
 {
     StyleVisualData* data = visual.access();
-    data->clip.m_top = top;
-    data->clip.m_right = right;
-    data->clip.m_bottom = bottom;
-    data->clip.m_left = left;
+    data->clip.top() = top;
+    data->clip.right() = right;
+    data->clip.bottom() = bottom;
+    data->clip.left() = left;
 }
 
 void RenderStyle::addCursor(PassRefPtr<StyleImage> image, const IntPoint& hotSpot)
@@ -1309,10 +1309,10 @@ const Vector<StyleDashboardRegion>& RenderStyle::noneDashboardRegions()
     if (!noneListInitialized) {
         StyleDashboardRegion region;
         region.label = "";
-        region.offset.m_top  = Length();
-        region.offset.m_right = Length();
-        region.offset.m_bottom = Length();
-        region.offset.m_left = Length();
+        region.offset.top()  = Length();
+        region.offset.right() = Length();
+        region.offset.bottom() = Length();
+        region.offset.left() = Length();
         region.type = StyleDashboardRegion::None;
         noneList.append(region);
         noneListInitialized = true;
index dbc2c43de5b65f89dafc3b7eed3744c18f4c0a03..dfa5441a63b803f87fa1f6127437f78dd4711025 100644 (file)
@@ -37,7 +37,6 @@
 #include "FontBaseline.h"
 #include "FontDescription.h"
 #include "GraphicsTypes.h"
-#include "LayoutBoxExtent.h"
 #include "Length.h"
 #include "LengthBox.h"
 #include "LengthFunctions.h"
@@ -531,12 +530,12 @@ public:
     bool operator==(const RenderStyle& other) const;
     bool operator!=(const RenderStyle& other) const { return !(*this == other); }
     bool isFloating() const { return noninherited_flags.isFloating(); }
-    bool hasMargin() const { return surround->margin.nonZero(); }
+    bool hasMargin() const { return !surround->margin.isZero(); }
     bool hasBorder() const { return surround->border.hasBorder(); }
     bool hasBorderFill() const { return surround->border.hasFill(); }
     bool hasBorderDecoration() const { return hasBorder() || hasBorderFill(); }
-    bool hasPadding() const { return surround->padding.nonZero(); }
-    bool hasOffset() const { return surround->offset.nonZero(); }
+    bool hasPadding() const { return !surround->padding.isZero(); }
+    bool hasOffset() const { return !surround->offset.isZero(); }
     bool hasMarginBeforeQuirk() const { return marginBefore().hasQuirk(); }
     bool hasMarginAfterQuirk() const { return marginAfter().hasQuirk(); }
 
@@ -558,7 +557,7 @@ public:
     LayoutBoxExtent imageOutsets(const NinePieceImage&) const;
     bool hasBorderImageOutsets() const
     {
-        return borderImage().hasImage() && borderImage().outset().nonZero();
+        return borderImage().hasImage() && !borderImage().outset().isZero();
     }
     LayoutBoxExtent borderImageOutsets() const
     {
@@ -595,8 +594,8 @@ public:
     const Length& bottom() const { return surround->offset.bottom(); }
 
     // Accessors for positioned object edges that take into account writing mode.
-    const Length& logicalLeft() const { return surround->offset.logicalLeft(writingMode()); }
-    const Length& logicalRight() const { return surround->offset.logicalRight(writingMode()); }
+    const Length& logicalLeft() const { return surround->offset.start(writingMode()); }
+    const Length& logicalRight() const { return surround->offset.end(writingMode()); }
     const Length& logicalTop() const { return surround->offset.before(writingMode()); }
     const Length& logicalBottom() const { return surround->offset.after(writingMode()); }
 
@@ -662,7 +661,8 @@ public:
     float borderBottomWidth() const { return surround->border.borderBottomWidth(); }
     EBorderStyle borderBottomStyle() const { return surround->border.bottom().style(); }
     bool borderBottomIsTransparent() const { return surround->border.bottom().isTransparent(); }
-    
+    FloatBoxExtent borderWidth() const { return surround->border.borderWidth(); }
+
     float borderBeforeWidth() const;
     float borderAfterWidth() const;
     float borderStartWidth() const;
@@ -1200,10 +1200,10 @@ public:
     void setPosition(EPosition v) { noninherited_flags.setPosition(v); }
     void setFloating(EFloat v) { noninherited_flags.setFloating(v); }
 
-    void setLeft(Length v) { SET_VAR(surround, offset.m_left, WTF::move(v)); }
-    void setRight(Length v) { SET_VAR(surround, offset.m_right, WTF::move(v)); }
-    void setTop(Length v) { SET_VAR(surround, offset.m_top, WTF::move(v)); }
-    void setBottom(Length v) { SET_VAR(surround, offset.m_bottom, WTF::move(v)); }
+    void setLeft(Length v) { SET_VAR(surround, offset.left(), WTF::move(v)); }
+    void setRight(Length v) { SET_VAR(surround, offset.right(), WTF::move(v)); }
+    void setTop(Length v) { SET_VAR(surround, offset.top(), WTF::move(v)); }
+    void setBottom(Length v) { SET_VAR(surround, offset.bottom(), WTF::move(v)); }
 
     void setWidth(Length v) { SET_VAR(m_box, m_width, WTF::move(v)); }
     void setHeight(Length v) { SET_VAR(m_box, m_height, WTF::move(v)); }
@@ -1239,10 +1239,10 @@ public:
     {
         StyleDashboardRegion region;
         region.label = label;
-        region.offset.m_top = WTF::move(t);
-        region.offset.m_right = WTF::move(r);
-        region.offset.m_bottom = WTF::move(b);
-        region.offset.m_left = WTF::move(l);
+        region.offset.top() = WTF::move(t);
+        region.offset.right() = WTF::move(r);
+        region.offset.bottom() = WTF::move(b);
+        region.offset.left() = WTF::move(l);
         region.type = type;
         if (!append)
             rareNonInheritedData.access()->m_dashboardRegions.clear();
@@ -1323,10 +1323,10 @@ public:
     void setVerticalAlignLength(Length length) { setVerticalAlign(LENGTH); SET_VAR(m_box, m_verticalAlign, WTF::move(length)); }
 
     void setHasClip(bool b = true) { SET_VAR(visual, hasClip, b); }
-    void setClipLeft(Length length) { SET_VAR(visual, clip.m_left, WTF::move(length)); }
-    void setClipRight(Length length) { SET_VAR(visual, clip.m_right, WTF::move(length)); }
-    void setClipTop(Length length) { SET_VAR(visual, clip.m_top, WTF::move(length)); }
-    void setClipBottom(Length length) { SET_VAR(visual, clip.m_bottom, WTF::move(length)); }
+    void setClipLeft(Length length) { SET_VAR(visual, clip.left(), WTF::move(length)); }
+    void setClipRight(Length length) { SET_VAR(visual, clip.right(), WTF::move(length)); }
+    void setClipTop(Length length) { SET_VAR(visual, clip.top(), WTF::move(length)); }
+    void setClipBottom(Length length) { SET_VAR(visual, clip.bottom(), WTF::move(length)); }
     void setClip(Length top, Length right, Length bottom, Length left);
     void setClip(LengthBox box) { SET_VAR(visual, clip, WTF::move(box)); }
 
@@ -1434,19 +1434,19 @@ public:
     void setListStylePosition(EListStylePosition v) { inherited_flags._list_style_position = v; }
 
     void resetMargin() { SET_VAR(surround, margin, LengthBox(Fixed)); }
-    void setMarginTop(Length length) { SET_VAR(surround, margin.m_top, WTF::move(length)); }
-    void setMarginBottom(Length length) { SET_VAR(surround, margin.m_bottom, WTF::move(length)); }
-    void setMarginLeft(Length length) { SET_VAR(surround, margin.m_left, WTF::move(length)); }
-    void setMarginRight(Length length) { SET_VAR(surround, margin.m_right, WTF::move(length)); }
+    void setMarginTop(Length length) { SET_VAR(surround, margin.top(), WTF::move(length)); }
+    void setMarginBottom(Length length) { SET_VAR(surround, margin.bottom(), WTF::move(length)); }
+    void setMarginLeft(Length length) { SET_VAR(surround, margin.left(), WTF::move(length)); }
+    void setMarginRight(Length length) { SET_VAR(surround, margin.right(), WTF::move(length)); }
     void setMarginStart(Length);
     void setMarginEnd(Length);
 
     void resetPadding() { SET_VAR(surround, padding, LengthBox(Auto)); }
     void setPaddingBox(LengthBox box) { SET_VAR(surround, padding, WTF::move(box)); }
-    void setPaddingTop(Length length) { SET_VAR(surround, padding.m_top, WTF::move(length)); }
-    void setPaddingBottom(Length length) { SET_VAR(surround, padding.m_bottom, WTF::move(length)); }
-    void setPaddingLeft(Length length) { SET_VAR(surround, padding.m_left, WTF::move(length)); }
-    void setPaddingRight(Length length) { SET_VAR(surround, padding.m_right, WTF::move(length)); }
+    void setPaddingTop(Length length) { SET_VAR(surround, padding.top(), WTF::move(length)); }
+    void setPaddingBottom(Length length) { SET_VAR(surround, padding.bottom(), WTF::move(length)); }
+    void setPaddingLeft(Length length) { SET_VAR(surround, padding.left(), WTF::move(length)); }
+    void setPaddingRight(Length length) { SET_VAR(surround, padding.right(), WTF::move(length)); }
 
     void setCursor(ECursor c) { inherited_flags._cursor_style = c; }
     void addCursor(PassRefPtr<StyleImage>, const IntPoint& hotSpot = IntPoint());