diff --git a/yoga/YGNode.cpp b/yoga/YGNode.cpp index 2c68d607..172da871 100644 --- a/yoga/YGNode.cpp +++ b/yoga/YGNode.cpp @@ -22,6 +22,7 @@ YGNode::YGNode(YGNode&& node) { measureUsesContext_ = node.measureUsesContext_; baselineUsesContext_ = node.baselineUsesContext_; printUsesContext_ = node.printUsesContext_; + useWebDefaults_ = node.useWebDefaults_; measure_ = node.measure_; baseline_ = node.baseline_; print_ = node.print_; @@ -38,6 +39,13 @@ YGNode::YGNode(YGNode&& node) { } } +YGNode::YGNode(const YGNode& node, YGConfigRef config) : YGNode{node} { + config_ = config; + if (config->useWebDefaults) { + useWebDefaults(); + } +} + void YGNode::print(void* printContext) { if (print_.noContext != nullptr) { if (printUsesContext_) { @@ -349,7 +357,7 @@ YGValue YGNode::resolveFlexBasisPtr() const { return flexBasis; } if (!style_.flex().isUndefined() && style_.flex().unwrap() > 0.0f) { - return config_->useWebDefaults ? YGValueAuto : YGValueZero; + return useWebDefaults_ ? YGValueAuto : YGValueZero; } return YGValueAuto; } @@ -425,11 +433,11 @@ float YGNode::resolveFlexShrink() const { if (!style_.flexShrink().isUndefined()) { return style_.flexShrink().unwrap(); } - if (!config_->useWebDefaults && !style_.flex().isUndefined() && + if (!useWebDefaults_ && !style_.flex().isUndefined() && style_.flex().unwrap() < 0.0f) { return -style_.flex().unwrap(); } - return config_->useWebDefaults ? kWebDefaultFlexShrink : kDefaultFlexShrink; + return useWebDefaults_ ? kWebDefaultFlexShrink : kDefaultFlexShrink; } bool YGNode::isNodeFlexible() { @@ -581,11 +589,9 @@ void YGNode::reset() { clearChildren(); - auto config = getConfig(); - *this = YGNode{}; - if (config->useWebDefaults) { - style_.flexDirection() = YGFlexDirectionRow; - style_.alignContent() = YGAlignStretch; + auto webDefaults = useWebDefaults_; + *this = YGNode{getConfig()}; + if (webDefaults) { + useWebDefaults(); } - setConfig(config); } diff --git a/yoga/YGNode.h b/yoga/YGNode.h index bbd1b703..d368bde0 100644 --- a/yoga/YGNode.h +++ b/yoga/YGNode.h @@ -13,6 +13,8 @@ #include "YGStyle.h" #include "Yoga-internal.h" +YGConfigRef YGConfigGetDefault(); + struct YGNode { using MeasureWithContextFn = YGSize (*)(YGNode*, float, YGMeasureMode, float, YGMeasureMode, void*); @@ -28,6 +30,7 @@ private: bool measureUsesContext_ : 1; bool baselineUsesContext_ : 1; bool printUsesContext_ : 1; + bool useWebDefaults_ : 1; uint8_t reserved_ = 0; union { YGMeasureFunc noContext; @@ -58,6 +61,12 @@ private: void setMeasureFunc(decltype(measure_)); void setBaselineFunc(decltype(baseline_)); + void useWebDefaults() { + useWebDefaults_ = true; + style_.flexDirection() = YGFlexDirectionRow; + style_.alignContent() = YGAlignStretch; + } + // DANGER DANGER DANGER! // If the the node assigned to has children, we'd either have to deallocate // them (potentially incorrect) or ignore them (danger of leaks). Only ever @@ -68,8 +77,8 @@ private: using CompactValue = facebook::yoga::detail::CompactValue; public: - YGNode() : YGNode{nullptr} {} - explicit YGNode(const YGConfigRef newConfig) + YGNode() : YGNode{YGConfigGetDefault()} {} + explicit YGNode(const YGConfigRef config) : hasNewLayout_{true}, isReferenceBaseline_{false}, isDirty_{false}, @@ -77,7 +86,12 @@ public: measureUsesContext_{false}, baselineUsesContext_{false}, printUsesContext_{false}, - config_{newConfig} {}; + useWebDefaults_{config->useWebDefaults}, + config_{config} { + if (useWebDefaults_) { + useWebDefaults(); + } + }; ~YGNode() = default; // cleanup of owner/children relationships in YGNodeFree YGNode(YGNode&&); @@ -86,6 +100,9 @@ public: // Should we remove this? YGNode(const YGNode& node) = default; + // for RB fabric + YGNode(const YGNode& node, YGConfigRef config); + // assignment means potential leaks of existing children, or alternatively // freeing unowned memory, double free, or freeing stack memory. YGNode& operator=(const YGNode&) = delete; diff --git a/yoga/Yoga.cpp b/yoga/Yoga.cpp index f7322980..bcca9795 100644 --- a/yoga/Yoga.cpp +++ b/yoga/Yoga.cpp @@ -210,18 +210,13 @@ void YGNodeMarkDirtyAndPropogateToDescendants(const YGNodeRef node) { int32_t gConfigInstanceCount = 0; WIN_EXPORT YGNodeRef YGNodeNewWithConfig(const YGConfigRef config) { - const YGNodeRef node = new YGNode(); + const YGNodeRef node = new YGNode{config}; YGAssertWithConfig( config, node != nullptr, "Could not allocate memory for node"); #ifdef YG_ENABLE_EVENTS Event::publish(node, {config}); #endif - if (config->useWebDefaults) { - node->getStyle().flexDirection() = YGFlexDirectionRow; - node->getStyle().alignContent() = YGAlignStretch; - } - node->setConfig(config); return node; }