OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2011 Google Inc. All rights reserved. | 2 * Copyright (C) 2011 Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
(...skipping 428 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
439 // That's the logical width for horizontal writing modes, and the logical he
ight in vertical writing modes. | 439 // That's the logical width for horizontal writing modes, and the logical he
ight in vertical writing modes. |
440 // For a vertical flow, main size is the height, so it's the inverse. | 440 // For a vertical flow, main size is the height, so it's the inverse. |
441 // So we need the logical width if we have a horizontal flow and horizontal
writing mode, or vertical flow and vertical writing mode. | 441 // So we need the logical width if we have a horizontal flow and horizontal
writing mode, or vertical flow and vertical writing mode. |
442 // Otherwise we need the logical height. | 442 // Otherwise we need the logical height. |
443 if (isHorizontalFlow() != child.styleRef().isHorizontalWritingMode()) { | 443 if (isHorizontalFlow() != child.styleRef().isHorizontalWritingMode()) { |
444 // We don't have to check for "auto" here - computeContentLogicalHeight
will just return -1 for that case anyway. | 444 // We don't have to check for "auto" here - computeContentLogicalHeight
will just return -1 for that case anyway. |
445 // It's safe to access scrollbarLogicalHeight here because computeNextFl
exLine will have already | 445 // It's safe to access scrollbarLogicalHeight here because computeNextFl
exLine will have already |
446 // forced layout on the child. | 446 // forced layout on the child. |
447 return child.computeContentLogicalHeight(sizeType, size, child.contentLo
gicalHeight()) + child.scrollbarLogicalHeight(); | 447 return child.computeContentLogicalHeight(sizeType, size, child.contentLo
gicalHeight()) + child.scrollbarLogicalHeight(); |
448 } | 448 } |
449 return child.computeLogicalWidthUsing(sizeType, size, contentLogicalWidth(),
this) - child.borderAndPaddingLogicalWidth(); | 449 // computeLogicalWidth always re-computes the intrinsic widths. However, whe
n our logical width is auto, |
| 450 // we can just use our cached value. So let's do that here. (Compare code in
LayoutBlock::computePreferredLogicalWidths) |
| 451 LayoutUnit borderAndPadding = child.borderAndPaddingLogicalWidth(); |
| 452 if (styleRef().logicalWidth().isAuto()) { |
| 453 if (size.type() == MinContent) |
| 454 return child.minPreferredLogicalWidth() - borderAndPadding; |
| 455 if (size.type() == MaxContent) |
| 456 return child.maxPreferredLogicalWidth() - borderAndPadding; |
| 457 } |
| 458 return child.computeLogicalWidthUsing(sizeType, size, contentLogicalWidth(),
this) - borderAndPadding; |
450 } | 459 } |
451 | 460 |
452 WritingMode LayoutFlexibleBox::transformedWritingMode() const | 461 WritingMode LayoutFlexibleBox::transformedWritingMode() const |
453 { | 462 { |
454 WritingMode mode = style()->writingMode(); | 463 WritingMode mode = style()->writingMode(); |
455 if (!isColumnFlow()) | 464 if (!isColumnFlow()) |
456 return mode; | 465 return mode; |
457 | 466 |
458 switch (mode) { | 467 switch (mode) { |
459 case TopToBottomWritingMode: | 468 case TopToBottomWritingMode: |
(...skipping 403 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
863 if (isHorizontalFlow()) { | 872 if (isHorizontalFlow()) { |
864 child->setMarginLeft(computeChildMarginValue(child->style()->marginL
eft())); | 873 child->setMarginLeft(computeChildMarginValue(child->style()->marginL
eft())); |
865 child->setMarginRight(computeChildMarginValue(child->style()->margin
Right())); | 874 child->setMarginRight(computeChildMarginValue(child->style()->margin
Right())); |
866 } else { | 875 } else { |
867 child->setMarginTop(computeChildMarginValue(child->style()->marginTo
p())); | 876 child->setMarginTop(computeChildMarginValue(child->style()->marginTo
p())); |
868 child->setMarginBottom(computeChildMarginValue(child->style()->margi
nBottom())); | 877 child->setMarginBottom(computeChildMarginValue(child->style()->margi
nBottom())); |
869 } | 878 } |
870 } | 879 } |
871 } | 880 } |
872 | 881 |
873 LayoutUnit LayoutFlexibleBox::adjustChildSizeForMinAndMax(const LayoutBox& child
, LayoutUnit childSize, bool childShrunk) | 882 LayoutUnit LayoutFlexibleBox::adjustChildSizeForMinAndMax(const LayoutBox& child
, LayoutUnit childSize) |
874 { | 883 { |
875 Length max = isHorizontalFlow() ? child.style()->maxWidth() : child.style()-
>maxHeight(); | 884 Length max = isHorizontalFlow() ? child.style()->maxWidth() : child.style()-
>maxHeight(); |
876 LayoutUnit maxExtent = -1; | 885 LayoutUnit maxExtent = -1; |
877 if (max.isSpecifiedOrIntrinsic()) { | 886 if (max.isSpecifiedOrIntrinsic()) { |
878 maxExtent = computeMainAxisExtentForChild(child, MaxSize, max); | 887 maxExtent = computeMainAxisExtentForChild(child, MaxSize, max); |
879 ASSERT(maxExtent >= -1); | 888 ASSERT(maxExtent >= -1); |
880 if (maxExtent != -1 && childSize > maxExtent) | 889 if (maxExtent != -1 && childSize > maxExtent) |
881 childSize = maxExtent; | 890 childSize = maxExtent; |
882 } | 891 } |
883 | 892 |
884 Length min = isHorizontalFlow() ? child.style()->minWidth() : child.style()-
>minHeight(); | 893 Length min = isHorizontalFlow() ? child.style()->minWidth() : child.style()-
>minHeight(); |
885 LayoutUnit minExtent = 0; | 894 LayoutUnit minExtent = 0; |
886 if (min.isSpecifiedOrIntrinsic()) { | 895 if (min.isSpecifiedOrIntrinsic()) { |
887 minExtent = computeMainAxisExtentForChild(child, MinSize, min); | 896 minExtent = computeMainAxisExtentForChild(child, MinSize, min); |
888 // computeMainAxisExtentForChild can return -1 when the child has a perc
entage | 897 // computeMainAxisExtentForChild can return -1 when the child has a perc
entage |
889 // min size, but we have an indefinite size in that axis. | 898 // min size, but we have an indefinite size in that axis. |
890 minExtent = std::max(LayoutUnit(), minExtent); | 899 minExtent = std::max(LayoutUnit(), minExtent); |
891 } else if (childShrunk && min.isAuto() && mainAxisOverflowForChild(child) ==
OVISIBLE) { | 900 } else if (min.isAuto() && mainAxisOverflowForChild(child) == OVISIBLE) { |
892 // css-flexbox section 4.5 | 901 // css-flexbox section 4.5 |
893 LayoutUnit contentSize = computeMainAxisExtentForChild(child, MinSize, L
ength(MinContent)); | 902 LayoutUnit contentSize = computeMainAxisExtentForChild(child, MinSize, L
ength(MinContent)); |
894 ASSERT(contentSize >= 0); | 903 ASSERT(contentSize >= 0); |
895 if (maxExtent != -1 && contentSize > maxExtent) | 904 if (maxExtent != -1 && contentSize > maxExtent) |
896 contentSize = maxExtent; | 905 contentSize = maxExtent; |
897 | 906 |
898 Length mainSize = isHorizontalFlow() ? child.styleRef().width() : child.
styleRef().height(); | 907 Length mainSize = isHorizontalFlow() ? child.styleRef().width() : child.
styleRef().height(); |
899 if (mainAxisLengthIsDefinite(child, mainSize)) { | 908 if (mainAxisLengthIsDefinite(child, mainSize)) { |
900 LayoutUnit resolvedMainSize = computeMainAxisExtentForChild(child, M
ainOrPreferredSize, mainSize); | 909 LayoutUnit resolvedMainSize = computeMainAxisExtentForChild(child, M
ainOrPreferredSize, mainSize); |
901 ASSERT(resolvedMainSize >= 0); | 910 ASSERT(resolvedMainSize >= 0); |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
987 childSizes.append(0); | 996 childSizes.append(0); |
988 continue; | 997 continue; |
989 } | 998 } |
990 | 999 |
991 if (inflexibleItems.contains(child)) { | 1000 if (inflexibleItems.contains(child)) { |
992 childSizes.append(inflexibleItems.get(child)); | 1001 childSizes.append(inflexibleItems.get(child)); |
993 } else { | 1002 } else { |
994 LayoutUnit childInnerFlexBaseSize = computeInnerFlexBaseSizeForChild
(*child); | 1003 LayoutUnit childInnerFlexBaseSize = computeInnerFlexBaseSizeForChild
(*child); |
995 LayoutUnit childSize = childInnerFlexBaseSize; | 1004 LayoutUnit childSize = childInnerFlexBaseSize; |
996 double extraSpace = 0; | 1005 double extraSpace = 0; |
997 bool childShrunk = false; | |
998 if (availableFreeSpace > 0 && totalFlexGrow > 0 && flexSign == Posit
iveFlexibility && std::isfinite(totalFlexGrow)) { | 1006 if (availableFreeSpace > 0 && totalFlexGrow > 0 && flexSign == Posit
iveFlexibility && std::isfinite(totalFlexGrow)) { |
999 if (totalFlexGrow < 1) | 1007 if (totalFlexGrow < 1) |
1000 extraSpace = availableFreeSpace * child->style()->flexGrow()
; | 1008 extraSpace = availableFreeSpace * child->style()->flexGrow()
; |
1001 else | 1009 else |
1002 extraSpace = availableFreeSpace * child->style()->flexGrow()
/ totalFlexGrow; | 1010 extraSpace = availableFreeSpace * child->style()->flexGrow()
/ totalFlexGrow; |
1003 } else if (availableFreeSpace < 0 && totalWeightedFlexShrink > 0 &&
flexSign == NegativeFlexibility && std::isfinite(totalWeightedFlexShrink) && chi
ld->style()->flexShrink()) { | 1011 } else if (availableFreeSpace < 0 && totalWeightedFlexShrink > 0 &&
flexSign == NegativeFlexibility && std::isfinite(totalWeightedFlexShrink) && chi
ld->style()->flexShrink()) { |
1004 extraSpace = availableFreeSpace * child->style()->flexShrink() *
childInnerFlexBaseSize / totalWeightedFlexShrink; | 1012 extraSpace = availableFreeSpace * child->style()->flexShrink() *
childInnerFlexBaseSize / totalWeightedFlexShrink; |
1005 childShrunk = true; | |
1006 } | 1013 } |
1007 if (std::isfinite(extraSpace)) | 1014 if (std::isfinite(extraSpace)) |
1008 childSize += LayoutUnit::fromFloatRound(extraSpace); | 1015 childSize += LayoutUnit::fromFloatRound(extraSpace); |
1009 | 1016 |
1010 LayoutUnit adjustedChildSize = adjustChildSizeForMinAndMax(*child, c
hildSize, childShrunk); | 1017 LayoutUnit adjustedChildSize = adjustChildSizeForMinAndMax(*child, c
hildSize); |
1011 ASSERT(adjustedChildSize >= 0); | 1018 ASSERT(adjustedChildSize >= 0); |
1012 childSizes.append(adjustedChildSize); | 1019 childSizes.append(adjustedChildSize); |
1013 usedFreeSpace += adjustedChildSize - childInnerFlexBaseSize; | 1020 usedFreeSpace += adjustedChildSize - childInnerFlexBaseSize; |
1014 | 1021 |
1015 LayoutUnit violation = adjustedChildSize - childSize; | 1022 LayoutUnit violation = adjustedChildSize - childSize; |
1016 if (violation > 0) | 1023 if (violation > 0) |
1017 minViolations.append(Violation(child, adjustedChildSize, childIn
nerFlexBaseSize)); | 1024 minViolations.append(Violation(child, adjustedChildSize, childIn
nerFlexBaseSize)); |
1018 else if (violation < 0) | 1025 else if (violation < 0) |
1019 maxViolations.append(Violation(child, adjustedChildSize, childIn
nerFlexBaseSize)); | 1026 maxViolations.append(Violation(child, adjustedChildSize, childIn
nerFlexBaseSize)); |
1020 totalViolation += violation; | 1027 totalViolation += violation; |
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1140 return isHorizontalFlow() && child.style()->height().isAuto(); | 1147 return isHorizontalFlow() && child.style()->height().isAuto(); |
1141 } | 1148 } |
1142 | 1149 |
1143 bool LayoutFlexibleBox::childHasIntrinsicMainAxisSize(const LayoutBox& child) co
nst | 1150 bool LayoutFlexibleBox::childHasIntrinsicMainAxisSize(const LayoutBox& child) co
nst |
1144 { | 1151 { |
1145 bool result = false; | 1152 bool result = false; |
1146 if (isHorizontalFlow() != child.styleRef().isHorizontalWritingMode()) { | 1153 if (isHorizontalFlow() != child.styleRef().isHorizontalWritingMode()) { |
1147 Length childFlexBasis = flexBasisForChild(child); | 1154 Length childFlexBasis = flexBasisForChild(child); |
1148 Length childMinSize = isHorizontalFlow() ? child.style()->minWidth() : c
hild.style()->minHeight(); | 1155 Length childMinSize = isHorizontalFlow() ? child.style()->minWidth() : c
hild.style()->minHeight(); |
1149 Length childMaxSize = isHorizontalFlow() ? child.style()->maxWidth() : c
hild.style()->maxHeight(); | 1156 Length childMaxSize = isHorizontalFlow() ? child.style()->maxWidth() : c
hild.style()->maxHeight(); |
1150 if (childFlexBasis.isIntrinsic() || childMinSize.isIntrinsic() || childM
axSize.isIntrinsic()) | 1157 if (childFlexBasis.isIntrinsic() || childMinSize.isIntrinsicOrAuto() ||
childMaxSize.isIntrinsic()) |
1151 result = true; | 1158 result = true; |
1152 } | 1159 } |
1153 return result; | 1160 return result; |
1154 } | 1161 } |
1155 | 1162 |
1156 EOverflow LayoutFlexibleBox::mainAxisOverflowForChild(const LayoutBox& child) co
nst | 1163 EOverflow LayoutFlexibleBox::mainAxisOverflowForChild(const LayoutBox& child) co
nst |
1157 { | 1164 { |
1158 if (isHorizontalFlow()) | 1165 if (isHorizontalFlow()) |
1159 return child.styleRef().overflowX(); | 1166 return child.styleRef().overflowX(); |
1160 return child.styleRef().overflowY(); | 1167 return child.styleRef().overflowY(); |
(...skipping 350 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1511 ASSERT(child); | 1518 ASSERT(child); |
1512 LayoutUnit lineCrossAxisExtent = lineContexts[lineNumber].crossAxisE
xtent; | 1519 LayoutUnit lineCrossAxisExtent = lineContexts[lineNumber].crossAxisE
xtent; |
1513 LayoutUnit originalOffset = lineContexts[lineNumber].crossAxisOffset
- crossAxisStartEdge; | 1520 LayoutUnit originalOffset = lineContexts[lineNumber].crossAxisOffset
- crossAxisStartEdge; |
1514 LayoutUnit newOffset = contentExtent - originalOffset - lineCrossAxi
sExtent; | 1521 LayoutUnit newOffset = contentExtent - originalOffset - lineCrossAxi
sExtent; |
1515 adjustAlignmentForChild(*child, newOffset - originalOffset); | 1522 adjustAlignmentForChild(*child, newOffset - originalOffset); |
1516 } | 1523 } |
1517 } | 1524 } |
1518 } | 1525 } |
1519 | 1526 |
1520 } | 1527 } |
OLD | NEW |