JNI: Simplify node context
Summary: @public Contexts of nodes only hold a bit mask after we got rid of weak JNI refs. We can simply store that data in a pointer-sized unsigned int. Here, we replace all context heap allocations with usage of the node context (`void *`) as bitmask. We also add a couple of utility operators in order to keep the code comprehensible. Reviewed By: fabiomassimo Differential Revision: D14425742 fbshipit-source-id: f32c2184a1f09268c39dbb8cd09ac96517339674
This commit is contained in:
committed by
Facebook Github Bot
parent
f039835249
commit
1471be54e3
@@ -8,6 +8,7 @@
|
|||||||
#include <yoga/YGNode.h>
|
#include <yoga/YGNode.h>
|
||||||
#include <yoga/Yoga.h>
|
#include <yoga/Yoga.h>
|
||||||
#include <yoga/log.h>
|
#include <yoga/log.h>
|
||||||
|
#include <cstdint>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <map>
|
#include <map>
|
||||||
|
|
||||||
@@ -88,17 +89,46 @@ public:
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct YGNodeContext {
|
namespace {
|
||||||
int edgeSetFlag = 0;
|
|
||||||
|
union YGNodeContext {
|
||||||
|
uintptr_t edgesSet = 0;
|
||||||
|
void* asVoidPtr;
|
||||||
};
|
};
|
||||||
|
|
||||||
const int MARGIN = 1;
|
class YGNodeEdges {
|
||||||
const int PADDING = 2;
|
uintptr_t edges_;
|
||||||
const int BORDER = 4;
|
|
||||||
|
|
||||||
static inline YGNodeContext* ygNodeRefToYGNodeContext(YGNodeRef node) {
|
public:
|
||||||
return reinterpret_cast<YGNodeContext*>(node->getContext());
|
enum Edge {
|
||||||
}
|
MARGIN = 1,
|
||||||
|
PADDING = 2,
|
||||||
|
BORDER = 4,
|
||||||
|
};
|
||||||
|
|
||||||
|
YGNodeEdges(YGNodeRef node) {
|
||||||
|
auto context = YGNodeContext{};
|
||||||
|
context.asVoidPtr = node->getContext();
|
||||||
|
edges_ = context.edgesSet;
|
||||||
|
}
|
||||||
|
|
||||||
|
void setOn(YGNodeRef node) {
|
||||||
|
auto context = YGNodeContext{};
|
||||||
|
context.edgesSet = edges_;
|
||||||
|
node->setContext(context.asVoidPtr);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool has(Edge edge) {
|
||||||
|
return (edges_ & edge) == edge;
|
||||||
|
}
|
||||||
|
|
||||||
|
YGNodeEdges& add(Edge edge) {
|
||||||
|
edges_ |= edge;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace
|
||||||
|
|
||||||
static inline local_ref<JYogaNode> YGNodeJobject(
|
static inline local_ref<JYogaNode> YGNodeJobject(
|
||||||
YGNodeRef node,
|
YGNodeRef node,
|
||||||
@@ -131,7 +161,7 @@ static void YGTransferLayoutOutputsRecursive(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
int edgeSetFlag = ygNodeRefToYGNodeContext(root)->edgeSetFlag;
|
auto edgesSet = YGNodeEdges{root};
|
||||||
|
|
||||||
static auto widthField = obj->getClass()->getField<jfloat>("mWidth");
|
static auto widthField = obj->getClass()->getField<jfloat>("mWidth");
|
||||||
static auto heightField = obj->getClass()->getField<jfloat>("mHeight");
|
static auto heightField = obj->getClass()->getField<jfloat>("mHeight");
|
||||||
@@ -178,7 +208,7 @@ static void YGTransferLayoutOutputsRecursive(
|
|||||||
obj->setFieldValue<jboolean>(hasNewLayoutField, true);
|
obj->setFieldValue<jboolean>(hasNewLayoutField, true);
|
||||||
YGTransferLayoutDirection(root, obj);
|
YGTransferLayoutDirection(root, obj);
|
||||||
|
|
||||||
if ((edgeSetFlag & MARGIN) == MARGIN) {
|
if (edgesSet.has(YGNodeEdges::MARGIN)) {
|
||||||
obj->setFieldValue(
|
obj->setFieldValue(
|
||||||
marginLeftField, YGNodeLayoutGetMargin(root, YGEdgeLeft));
|
marginLeftField, YGNodeLayoutGetMargin(root, YGEdgeLeft));
|
||||||
obj->setFieldValue(marginTopField, YGNodeLayoutGetMargin(root, YGEdgeTop));
|
obj->setFieldValue(marginTopField, YGNodeLayoutGetMargin(root, YGEdgeTop));
|
||||||
@@ -188,7 +218,7 @@ static void YGTransferLayoutOutputsRecursive(
|
|||||||
marginBottomField, YGNodeLayoutGetMargin(root, YGEdgeBottom));
|
marginBottomField, YGNodeLayoutGetMargin(root, YGEdgeBottom));
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((edgeSetFlag & PADDING) == PADDING) {
|
if (edgesSet.has(YGNodeEdges::PADDING)) {
|
||||||
obj->setFieldValue(
|
obj->setFieldValue(
|
||||||
paddingLeftField, YGNodeLayoutGetPadding(root, YGEdgeLeft));
|
paddingLeftField, YGNodeLayoutGetPadding(root, YGEdgeLeft));
|
||||||
obj->setFieldValue(
|
obj->setFieldValue(
|
||||||
@@ -199,7 +229,7 @@ static void YGTransferLayoutOutputsRecursive(
|
|||||||
paddingBottomField, YGNodeLayoutGetPadding(root, YGEdgeBottom));
|
paddingBottomField, YGNodeLayoutGetPadding(root, YGEdgeBottom));
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((edgeSetFlag & BORDER) == BORDER) {
|
if (edgesSet.has(YGNodeEdges::BORDER)) {
|
||||||
obj->setFieldValue(
|
obj->setFieldValue(
|
||||||
borderLeftField, YGNodeLayoutGetBorder(root, YGEdgeLeft));
|
borderLeftField, YGNodeLayoutGetBorder(root, YGEdgeLeft));
|
||||||
obj->setFieldValue(borderTopField, YGNodeLayoutGetBorder(root, YGEdgeTop));
|
obj->setFieldValue(borderTopField, YGNodeLayoutGetBorder(root, YGEdgeTop));
|
||||||
@@ -310,20 +340,16 @@ static int YGJNILogFunc(
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
YGNodeContext* createYGNodeContext() {
|
|
||||||
return new YGNodeContext();
|
|
||||||
}
|
|
||||||
|
|
||||||
jlong jni_YGNodeNew(alias_ref<jobject>) {
|
jlong jni_YGNodeNew(alias_ref<jobject>) {
|
||||||
const YGNodeRef node = YGNodeNew();
|
const YGNodeRef node = YGNodeNew();
|
||||||
node->setContext(createYGNodeContext());
|
node->setContext(YGNodeContext{}.asVoidPtr);
|
||||||
node->setPrintFunc(YGPrint);
|
node->setPrintFunc(YGPrint);
|
||||||
return reinterpret_cast<jlong>(node);
|
return reinterpret_cast<jlong>(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
jlong jni_YGNodeNewWithConfig(alias_ref<jobject>, jlong configPointer) {
|
jlong jni_YGNodeNewWithConfig(alias_ref<jobject>, jlong configPointer) {
|
||||||
const YGNodeRef node = YGNodeNewWithConfig(_jlong2YGConfigRef(configPointer));
|
const YGNodeRef node = YGNodeNewWithConfig(_jlong2YGConfigRef(configPointer));
|
||||||
node->setContext(createYGNodeContext());
|
node->setContext(YGNodeContext{}.asVoidPtr);
|
||||||
return reinterpret_cast<jlong>(node);
|
return reinterpret_cast<jlong>(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -332,10 +358,6 @@ void jni_YGNodeFree(alias_ref<jclass>, jlong nativePointer) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const YGNodeRef node = _jlong2YGNodeRef(nativePointer);
|
const YGNodeRef node = _jlong2YGNodeRef(nativePointer);
|
||||||
auto context = node->getContext();
|
|
||||||
if (context != nullptr) {
|
|
||||||
delete reinterpret_cast<YGNodeContext*>(node->getContext());
|
|
||||||
}
|
|
||||||
YGNodeFree(node);
|
YGNodeFree(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -642,6 +664,7 @@ static void YGNodeSetStyleInputs(
|
|||||||
float* styleInputs,
|
float* styleInputs,
|
||||||
int size) {
|
int size) {
|
||||||
const auto end = styleInputs + size;
|
const auto end = styleInputs + size;
|
||||||
|
auto edgesSet = YGNodeEdges{node};
|
||||||
while (styleInputs < end) {
|
while (styleInputs < end) {
|
||||||
auto styleInputKey = static_cast<YGStyleInput>((int) *styleInputs++);
|
auto styleInputKey = static_cast<YGStyleInput>((int) *styleInputs++);
|
||||||
switch (styleInputKey) {
|
switch (styleInputKey) {
|
||||||
@@ -744,40 +767,40 @@ static void YGNodeSetStyleInputs(
|
|||||||
case Margin: {
|
case Margin: {
|
||||||
auto edge = static_cast<YGEdge>(*styleInputs++);
|
auto edge = static_cast<YGEdge>(*styleInputs++);
|
||||||
float marginValue = *styleInputs++;
|
float marginValue = *styleInputs++;
|
||||||
ygNodeRefToYGNodeContext(node)->edgeSetFlag |= MARGIN;
|
edgesSet.add(YGNodeEdges::MARGIN);
|
||||||
YGNodeStyleSetMargin(node, edge, marginValue);
|
YGNodeStyleSetMargin(node, edge, marginValue);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case MarginPercent: {
|
case MarginPercent: {
|
||||||
auto edge = static_cast<YGEdge>(*styleInputs++);
|
auto edge = static_cast<YGEdge>(*styleInputs++);
|
||||||
float marginPercent = *styleInputs++;
|
float marginPercent = *styleInputs++;
|
||||||
ygNodeRefToYGNodeContext(node)->edgeSetFlag |= MARGIN;
|
edgesSet.add(YGNodeEdges::MARGIN);
|
||||||
YGNodeStyleSetMarginPercent(node, edge, marginPercent);
|
YGNodeStyleSetMarginPercent(node, edge, marginPercent);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case MarginAuto: {
|
case MarginAuto: {
|
||||||
ygNodeRefToYGNodeContext(node)->edgeSetFlag |= MARGIN;
|
edgesSet.add(YGNodeEdges::MARGIN);
|
||||||
YGNodeStyleSetMarginAuto(node, static_cast<YGEdge>(*styleInputs++));
|
YGNodeStyleSetMarginAuto(node, static_cast<YGEdge>(*styleInputs++));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Padding: {
|
case Padding: {
|
||||||
auto edge = static_cast<YGEdge>(*styleInputs++);
|
auto edge = static_cast<YGEdge>(*styleInputs++);
|
||||||
float paddingValue = *styleInputs++;
|
float paddingValue = *styleInputs++;
|
||||||
ygNodeRefToYGNodeContext(node)->edgeSetFlag |= PADDING;
|
edgesSet.add(YGNodeEdges::PADDING);
|
||||||
YGNodeStyleSetPadding(node, edge, paddingValue);
|
YGNodeStyleSetPadding(node, edge, paddingValue);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PaddingPercent: {
|
case PaddingPercent: {
|
||||||
auto edge = static_cast<YGEdge>(*styleInputs++);
|
auto edge = static_cast<YGEdge>(*styleInputs++);
|
||||||
float paddingPercent = *styleInputs++;
|
float paddingPercent = *styleInputs++;
|
||||||
ygNodeRefToYGNodeContext(node)->edgeSetFlag |= PADDING;
|
edgesSet.add(YGNodeEdges::PADDING);
|
||||||
YGNodeStyleSetPaddingPercent(node, edge, paddingPercent);
|
YGNodeStyleSetPaddingPercent(node, edge, paddingPercent);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Border: {
|
case Border: {
|
||||||
auto edge = static_cast<YGEdge>(*styleInputs++);
|
auto edge = static_cast<YGEdge>(*styleInputs++);
|
||||||
float borderValue = *styleInputs++;
|
float borderValue = *styleInputs++;
|
||||||
ygNodeRefToYGNodeContext(node)->edgeSetFlag |= BORDER;
|
edgesSet.add(YGNodeEdges::BORDER);
|
||||||
YGNodeStyleSetBorder(node, edge, borderValue);
|
YGNodeStyleSetBorder(node, edge, borderValue);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -801,6 +824,7 @@ static void YGNodeSetStyleInputs(
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
edgesSet.setOn(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
void jni_YGNodeSetStyleInputs(
|
void jni_YGNodeSetStyleInputs(
|
||||||
@@ -822,8 +846,7 @@ local_ref<jobject> jni_YGNodeStyleGetMargin(
|
|||||||
jlong nativePointer,
|
jlong nativePointer,
|
||||||
jint edge) {
|
jint edge) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
int edgeSetFlag = ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag;
|
if (!YGNodeEdges{yogaNodeRef}.has(YGNodeEdges::MARGIN)) {
|
||||||
if ((edgeSetFlag & MARGIN) != MARGIN) {
|
|
||||||
return JYogaValue::create(YGValueUndefined);
|
return JYogaValue::create(YGValueUndefined);
|
||||||
}
|
}
|
||||||
return JYogaValue::create(
|
return JYogaValue::create(
|
||||||
@@ -832,7 +855,7 @@ local_ref<jobject> jni_YGNodeStyleGetMargin(
|
|||||||
|
|
||||||
void jni_YGNodeStyleSetMargin(jlong nativePointer, jint edge, jfloat margin) {
|
void jni_YGNodeStyleSetMargin(jlong nativePointer, jint edge, jfloat margin) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag |= MARGIN;
|
YGNodeEdges{yogaNodeRef}.add(YGNodeEdges::MARGIN).setOn(yogaNodeRef);
|
||||||
YGNodeStyleSetMargin(
|
YGNodeStyleSetMargin(
|
||||||
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(margin));
|
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(margin));
|
||||||
}
|
}
|
||||||
@@ -842,14 +865,14 @@ void jni_YGNodeStyleSetMarginPercent(
|
|||||||
jint edge,
|
jint edge,
|
||||||
jfloat percent) {
|
jfloat percent) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag |= MARGIN;
|
YGNodeEdges{yogaNodeRef}.add(YGNodeEdges::MARGIN).setOn(yogaNodeRef);
|
||||||
YGNodeStyleSetMarginPercent(
|
YGNodeStyleSetMarginPercent(
|
||||||
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(percent));
|
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(percent));
|
||||||
}
|
}
|
||||||
|
|
||||||
void jni_YGNodeStyleSetMarginAuto(jlong nativePointer, jint edge) {
|
void jni_YGNodeStyleSetMarginAuto(jlong nativePointer, jint edge) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag |= MARGIN;
|
YGNodeEdges{yogaNodeRef}.add(YGNodeEdges::MARGIN).setOn(yogaNodeRef);
|
||||||
YGNodeStyleSetMarginAuto(yogaNodeRef, static_cast<YGEdge>(edge));
|
YGNodeStyleSetMarginAuto(yogaNodeRef, static_cast<YGEdge>(edge));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -858,8 +881,7 @@ local_ref<jobject> jni_YGNodeStyleGetPadding(
|
|||||||
jlong nativePointer,
|
jlong nativePointer,
|
||||||
jint edge) {
|
jint edge) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
int edgeSetFlag = ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag;
|
if (!YGNodeEdges{yogaNodeRef}.has(YGNodeEdges::PADDING)) {
|
||||||
if ((edgeSetFlag & PADDING) != PADDING) {
|
|
||||||
return JYogaValue::create(YGValueUndefined);
|
return JYogaValue::create(YGValueUndefined);
|
||||||
}
|
}
|
||||||
return JYogaValue::create(
|
return JYogaValue::create(
|
||||||
@@ -868,7 +890,7 @@ local_ref<jobject> jni_YGNodeStyleGetPadding(
|
|||||||
|
|
||||||
void jni_YGNodeStyleSetPadding(jlong nativePointer, jint edge, jfloat padding) {
|
void jni_YGNodeStyleSetPadding(jlong nativePointer, jint edge, jfloat padding) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag |= PADDING;
|
YGNodeEdges{yogaNodeRef}.add(YGNodeEdges::PADDING).setOn(yogaNodeRef);
|
||||||
YGNodeStyleSetPadding(
|
YGNodeStyleSetPadding(
|
||||||
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(padding));
|
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(padding));
|
||||||
}
|
}
|
||||||
@@ -878,15 +900,14 @@ void jni_YGNodeStyleSetPaddingPercent(
|
|||||||
jint edge,
|
jint edge,
|
||||||
jfloat percent) {
|
jfloat percent) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag |= PADDING;
|
YGNodeEdges{yogaNodeRef}.add(YGNodeEdges::PADDING).setOn(yogaNodeRef);
|
||||||
YGNodeStyleSetPaddingPercent(
|
YGNodeStyleSetPaddingPercent(
|
||||||
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(percent));
|
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(percent));
|
||||||
}
|
}
|
||||||
|
|
||||||
jfloat jni_YGNodeStyleGetBorder(jlong nativePointer, jint edge) {
|
jfloat jni_YGNodeStyleGetBorder(jlong nativePointer, jint edge) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
int edgeSetFlag = ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag;
|
if (!YGNodeEdges{yogaNodeRef}.has(YGNodeEdges::BORDER)) {
|
||||||
if ((edgeSetFlag & BORDER) != BORDER) {
|
|
||||||
return (jfloat) YGUndefined;
|
return (jfloat) YGUndefined;
|
||||||
}
|
}
|
||||||
return (jfloat) YGNodeStyleGetBorder(yogaNodeRef, static_cast<YGEdge>(edge));
|
return (jfloat) YGNodeStyleGetBorder(yogaNodeRef, static_cast<YGEdge>(edge));
|
||||||
@@ -894,7 +915,7 @@ jfloat jni_YGNodeStyleGetBorder(jlong nativePointer, jint edge) {
|
|||||||
|
|
||||||
void jni_YGNodeStyleSetBorder(jlong nativePointer, jint edge, jfloat border) {
|
void jni_YGNodeStyleSetBorder(jlong nativePointer, jint edge, jfloat border) {
|
||||||
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
YGNodeRef yogaNodeRef = _jlong2YGNodeRef(nativePointer);
|
||||||
ygNodeRefToYGNodeContext(yogaNodeRef)->edgeSetFlag |= BORDER;
|
YGNodeEdges{yogaNodeRef}.add(YGNodeEdges::BORDER).setOn(yogaNodeRef);
|
||||||
YGNodeStyleSetBorder(
|
YGNodeStyleSetBorder(
|
||||||
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(border));
|
yogaNodeRef, static_cast<YGEdge>(edge), static_cast<float>(border));
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user