Skip to content

Commit

Permalink
use fmod and YGDoubleEquals for double operations instead of float
Browse files Browse the repository at this point in the history
Summary: Changelog: [Internal][Yoga] Use double operations during rounding

Reviewed By: mdvacca

Differential Revision: D21840018

fbshipit-source-id: c5d17fcb8984b1da9832a15ccd4d628e8d742c6a
  • Loading branch information
SidharthGuglani-zz authored and facebook-github-bot committed Jun 8, 2020
1 parent 93019dc commit fc2b538
Show file tree
Hide file tree
Showing 3 changed files with 17 additions and 8 deletions.
7 changes: 7 additions & 0 deletions ReactCommon/yoga/yoga/Utils.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,13 @@ bool YGFloatsEqual(const float a, const float b) {
return yoga::isUndefined(a) && yoga::isUndefined(b);
}

bool YGDoubleEqual(const double a, const double b) {
if (!yoga::isUndefined(a) && !yoga::isUndefined(b)) {
return fabs(a - b) < 0.0001f;
}
return yoga::isUndefined(a) && yoga::isUndefined(b);
}

float YGFloatSanitize(const float val) {
return yoga::isUndefined(val) ? 0 : val;
}
Expand Down
2 changes: 2 additions & 0 deletions ReactCommon/yoga/yoga/Utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,8 @@ inline bool YGValueEqual(
// difference between two floats is less than 0.0001f or both are undefined.
bool YGFloatsEqual(const float a, const float b);

bool YGDoubleEqual(const double a, const double b);

float YGFloatMax(const float a, const float b);

YGFloatOptional YGFloatOptionalMax(
Expand Down
16 changes: 8 additions & 8 deletions ReactCommon/yoga/yoga/Yoga.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3668,7 +3668,7 @@ YOGA_EXPORT float YGRoundValueToPixelGrid(
double scaledValue = ((double) value) * pointScaleFactor;
// We want to calculate `fractial` such that `floor(scaledValue) = scaledValue
// - fractial`.
float fractial = fmodf(scaledValue, 1.0f);
double fractial = fmod(scaledValue, 1.0f);
if (fractial < 0) {
// This branch is for handling negative numbers for `value`.
//
Expand All @@ -3687,10 +3687,10 @@ YOGA_EXPORT float YGRoundValueToPixelGrid(
// - Finding the `floor`: -2.2 - fractial2 = -2.2 - 0.8 = -3
++fractial;
}
if (YGFloatsEqual(fractial, 0)) {
if (YGDoubleEqual(fractial, 0)) {
// First we check if the value is already rounded
scaledValue = scaledValue - fractial;
} else if (YGFloatsEqual(fractial, 1.0f)) {
} else if (YGDoubleEqual(fractial, 1.0f)) {
scaledValue = scaledValue - fractial + 1.0f;
} else if (forceCeil) {
// Next we check if we need to use forced rounding
Expand All @@ -3701,7 +3701,7 @@ YOGA_EXPORT float YGRoundValueToPixelGrid(
// Finally we just round the value
scaledValue = scaledValue - fractial +
(!YGFloatIsUndefined(fractial) &&
(fractial > 0.5f || YGFloatsEqual(fractial, 0.5f))
(fractial > 0.5f || YGDoubleEqual(fractial, 0.5f))
? 1.0f
: 0.0f);
}
Expand Down Expand Up @@ -4113,11 +4113,11 @@ static void YGRoundToPixelGrid(
// whole number, we don't have any fraction To verify if the result is close
// to whole number we want to check both floor and ceil numbers
const bool hasFractionalWidth =
!YGFloatsEqual(fmodf(nodeWidth * pointScaleFactor, 1.0), 0) &&
!YGFloatsEqual(fmodf(nodeWidth * pointScaleFactor, 1.0), 1.0);
!YGDoubleEqual(fmod(nodeWidth * pointScaleFactor, 1.0), 0) &&
!YGDoubleEqual(fmod(nodeWidth * pointScaleFactor, 1.0), 1.0);
const bool hasFractionalHeight =
!YGFloatsEqual(fmodf(nodeHeight * pointScaleFactor, 1.0), 0) &&
!YGFloatsEqual(fmodf(nodeHeight * pointScaleFactor, 1.0), 1.0);
!YGDoubleEqual(fmod(nodeHeight * pointScaleFactor, 1.0), 0) &&
!YGDoubleEqual(fmod(nodeHeight * pointScaleFactor, 1.0), 1.0);

node->setLayoutDimension(
YGRoundValueToPixelGrid(
Expand Down

0 comments on commit fc2b538

Please sign in to comment.