Baseline support #317

Closed
woehrl01 wants to merge 33 commits from baseline-support into master
14 changed files with 1021 additions and 3 deletions
Showing only changes of commit 71a23ef987 - Show all commits

View File

@@ -337,16 +337,16 @@ YGMeasureFunc YGNodeGetMeasureFunc(const YGNodeRef node) {
void YGNodeSetBaselineFunc(const YGNodeRef node, YGBaselineFunc baselineFunc) { void YGNodeSetBaselineFunc(const YGNodeRef node, YGBaselineFunc baselineFunc) {
if (baselineFunc == NULL) { if (baselineFunc == NULL) {
node->baseline = NULL; node->baseline = NULL;
} }
else { else {
node->baseline = baselineFunc; node->baseline = baselineFunc;
} }
} }
YGBaselineFunc YGNodeGetBaselineFunc(const YGNodeRef node) { YGBaselineFunc YGNodeGetBaselineFunc(const YGNodeRef node) {
return node->baseline; return node->baseline;
} }
void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32_t index) { void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32_t index) {
@@ -959,55 +959,55 @@ static inline YGDirection YGNodeResolveDirection(const YGNodeRef node,
static float YGBaselineOfFirstLine(const YGNodeRef node, const YGFlexDirection mainAxis, const float parentWidth) static float YGBaselineOfFirstLine(const YGNodeRef node, const YGFlexDirection mainAxis, const float parentWidth)
{ {
if(node->baseline != NULL) if(node->baseline != NULL)
{ {
return node->baseline(node); return node->baseline(node);
} }
YGNodeRef baselineChild = NULL; YGNodeRef baselineChild = NULL;
for(unsigned int i = 0; i < YGNodeGetChildCount(node); ++i) for(unsigned int i = 0; i < YGNodeGetChildCount(node); ++i)
{ {
const YGNodeRef child = YGNodeGetChild(node, i); const YGNodeRef child = YGNodeGetChild(node, i);
if(child->style.positionType == YGPositionTypeAbsolute || child->lineIndex > 0) if(child->style.positionType == YGPositionTypeAbsolute || child->lineIndex > 0)
{ {
continue; continue;
} }
if(YGNodeAlignItem(node, child) == YGAlignBaseline) if(YGNodeAlignItem(node, child) == YGAlignBaseline)
{ {
baselineChild = child; baselineChild = child;
break; break;
} }
if(baselineChild == NULL) if(baselineChild == NULL)
{ {
baselineChild = child; baselineChild = child;
} }
} }
if(baselineChild == NULL) if(baselineChild == NULL)
{ {
return YGUndefined; return YGUndefined;
} }
float baseline = YGBaselineOfFirstLine(baselineChild, node->style.direction, node->layout.measuredDimensions[YGDimensionWidth]); float baseline = YGBaselineOfFirstLine(baselineChild, node->style.direction, node->layout.measuredDimensions[YGDimensionWidth]);
if(YGFloatIsUndefined(baseline)) if(YGFloatIsUndefined(baseline))
{ {
baseline = YGNodeLeadingPaddingAndBorder(baselineChild, mainAxis, parentWidth) baseline = YGNodeLeadingPaddingAndBorder(baselineChild, mainAxis, parentWidth)
+ baselineChild->layout.measuredDimensions[dim[mainAxis]]; + baselineChild->layout.measuredDimensions[dim[mainAxis]];
} }
return baseline + baselineChild->layout.position[YGEdgeTop]; return baseline + baselineChild->layout.position[YGEdgeTop];
} }
static float YGBaselineWithMargin(const YGNodeRef node, const YGFlexDirection mainAxis, const float parentWidth) static float YGBaselineWithMargin(const YGNodeRef node, const YGFlexDirection mainAxis, const float parentWidth)
{ {
float baseline = YGBaselineOfFirstLine(node, mainAxis, parentWidth); float baseline = YGBaselineOfFirstLine(node, mainAxis, parentWidth);
emilsjolander commented 2017-01-05 12:09:44 -08:00 (Migrated from github.com)
Review

not quite sure why we break if a child has more than one line. That would mean if the first child of this node has two lines then the baseline would default to the height of the node. I'm not sure why that would be correct.

not quite sure why we break if a child has more than one line. That would mean if the first child of this node has two lines then the baseline would default to the height of the node. I'm not sure why that would be correct.
woehrl01 commented 2017-01-05 12:15:22 -08:00 (Migrated from github.com)
Review

we break as only childs on the first line which have align baseline are taken into account. I already added a testcase for this.

we break as only childs on the first line which have align baseline are taken into account. I already added a testcase for this.
woehrl01 commented 2017-01-05 12:21:22 -08:00 (Migrated from github.com)
Review

oh, I see the confusion, child->lineIndex does not mean that it has more than one line. It means it is itself on the seconds (or later) line.

oh, I see the confusion, ```child->lineIndex``` does not mean that it has more than one line. It means it is itself on the seconds (or later) line.
emilsjolander commented 2017-01-05 12:45:58 -08:00 (Migrated from github.com)
Review

@woehrl01 yeah that was my confusion, i'm not super familiar with the multi line code and read it too quickly 🐱

@woehrl01 yeah that was my confusion, i'm not super familiar with the multi line code and read it too quickly 🐱
if(YGFloatIsUndefined(baseline)) if(YGFloatIsUndefined(baseline))
{ {
baseline = node->layout.measuredDimensions[dim[mainAxis]]; baseline = node->layout.measuredDimensions[dim[mainAxis]];
} }
return baseline + YGNodeLeadingMargin(node, mainAxis, parentWidth); return baseline + YGNodeLeadingMargin(node, mainAxis, parentWidth);
} }
@@ -2512,7 +2512,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
break; break;
case YGAlignAuto: case YGAlignAuto:
case YGAlignFlexStart: case YGAlignFlexStart:
case YGAlignBaseline: case YGAlignBaseline:
break; break;
} }
@@ -2523,7 +2523,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
// compute the line's height and find the endIndex // compute the line's height and find the endIndex
float lineHeight = 0; float lineHeight = 0;
float maxAscentForCurrentLine = 0; float maxAscentForCurrentLine = 0;
for (ii = startIndex; ii < childCount; ii++) { for (ii = startIndex; ii < childCount; ii++) {
const YGNodeRef child = YGNodeListGet(node->children, ii); const YGNodeRef child = YGNodeListGet(node->children, ii);
@@ -2532,11 +2532,11 @@ static void YGNodelayoutImpl(const YGNodeRef node,
break; break;
} }
if (performLayout && YGNodeAlignItem(node, child) == YGAlignBaseline) if (performLayout && YGNodeAlignItem(node, child) == YGAlignBaseline)
{ {
maxAscentForCurrentLine = fmaxf(maxAscentForCurrentLine, maxAscentForCurrentLine = fmaxf(maxAscentForCurrentLine,
YGBaselineWithMargin(child, crossAxis, availableInnerWidth)); YGBaselineWithMargin(child, crossAxis, availableInnerWidth));
} }
if (YGNodeIsLayoutDimDefined(child, crossAxis)) { if (YGNodeIsLayoutDimDefined(child, crossAxis)) {
lineHeight = fmaxf(lineHeight, lineHeight = fmaxf(lineHeight,
@@ -2579,12 +2579,12 @@ static void YGNodelayoutImpl(const YGNodeRef node,
// (auto) crossAxis dimension. // (auto) crossAxis dimension.
break; break;
} }
case YGAlignBaseline: { case YGAlignBaseline: {
child->layout.position[pos[crossAxis]] = currentLead child->layout.position[pos[crossAxis]] = currentLead
+ maxAscentForCurrentLine - + maxAscentForCurrentLine -
YGBaselineWithMargin(child, crossAxis, availableInnerWidth);; YGBaselineWithMargin(child, crossAxis, availableInnerWidth);;
break; break;
} }
case YGAlignAuto: case YGAlignAuto:
break; break;
} }