Set layout outputs on java object from C

Summary: Set layout outputs on CSSNode from C after layout calculation finishes instead of relying on calling jni gettings from java code. This should be much more efficient as it avoids a lot of jni overhead and also allows for calling getLayoutWidth() etc multiple times without incurring a penalty.

Reviewed By: lexs

Differential Revision: D4077968

fbshipit-source-id: bce86ba610cd5ae36cfb45d78b2609c63a14cfa3
This commit is contained in:
Emil Sjolander
2016-10-27 10:52:12 -07:00
committed by Facebook Github Bot
parent 46823878a5
commit 2cac77eaa1
2 changed files with 57 additions and 32 deletions

View File

@@ -45,6 +45,17 @@ public class CSSNode implements CSSNodeAPI<CSSNode> {
private boolean mHasSetBorder = false;
private boolean mHasSetPosition = false;
@DoNotStrip
private float mWidth = CSSConstants.UNDEFINED;
@DoNotStrip
private float mHeight = CSSConstants.UNDEFINED;
@DoNotStrip
private float mTop = CSSConstants.UNDEFINED;
@DoNotStrip
private float mLeft = CSSConstants.UNDEFINED;
@DoNotStrip
private int mLayoutDirection = 0;
private native long jni_CSSNodeNew();
public CSSNode() {
mNativePointer = jni_CSSNodeNew();
@@ -73,6 +84,12 @@ public class CSSNode implements CSSNodeAPI<CSSNode> {
mHasSetBorder = false;
mHasSetPosition = false;
mWidth = CSSConstants.UNDEFINED;
mHeight = CSSConstants.UNDEFINED;
mTop = CSSConstants.UNDEFINED;
mLeft = CSSConstants.UNDEFINED;
mLayoutDirection = 0;
mMeasureFunction = null;
mData = null;
@@ -176,12 +193,6 @@ public class CSSNode implements CSSNodeAPI<CSSNode> {
jni_CSSNodeStyleSetDirection(mNativePointer, direction.ordinal());
}
private native int jni_CSSNodeLayoutGetDirection(long nativePointer);
@Override
public CSSDirection getLayoutDirection() {
return CSSDirection.values()[jni_CSSNodeLayoutGetDirection(mNativePointer)];
}
private native int jni_CSSNodeStyleGetFlexDirection(long nativePointer);
@Override
public CSSFlexDirection getFlexDirection() {
@@ -450,28 +461,29 @@ public class CSSNode implements CSSNodeAPI<CSSNode> {
jni_CSSNodeStyleSetMaxHeight(mNativePointer, maxheight);
}
private native float jni_CSSNodeLayoutGetLeft(long nativePointer);
@Override
public float getLayoutX() {
return jni_CSSNodeLayoutGetLeft(mNativePointer);
return mLeft;
}
private native float jni_CSSNodeLayoutGetTop(long nativePointer);
@Override
public float getLayoutY() {
return jni_CSSNodeLayoutGetTop(mNativePointer);
return mTop;
}
private native float jni_CSSNodeLayoutGetWidth(long nativePointer);
@Override
public float getLayoutWidth() {
return jni_CSSNodeLayoutGetWidth(mNativePointer);
return mWidth;
}
private native float jni_CSSNodeLayoutGetHeight(long nativePointer);
@Override
public float getLayoutHeight() {
return jni_CSSNodeLayoutGetHeight(mNativePointer);
return mHeight;
}
@Override
public CSSDirection getLayoutDirection() {
return CSSDirection.values()[mLayoutDirection];
}
private native void jni_CSSNodeSetHasMeasureFunc(long nativePointer, boolean hasMeasureFunc);

View File

@@ -14,6 +14,31 @@
using namespace facebook::jni;
using namespace std;
static void _jniTransferLayoutDirection(CSSNodeRef node, alias_ref<jobject> javaNode) {
static auto layoutDirectionField = javaNode->getClass()->getField<jint>("mLayoutDirection");
javaNode->setFieldValue(layoutDirectionField, static_cast<jint>(CSSNodeLayoutGetDirection(node)));
}
static void _jniTransferLayoutOutputsRecursive(CSSNodeRef root) {
auto javaNode = adopt_local(
Environment::current()->NewLocalRef(reinterpret_cast<jweak>(CSSNodeGetContext(root))));
static auto widthField = javaNode->getClass()->getField<jfloat>("mWidth");
static auto heightField = javaNode->getClass()->getField<jfloat>("mHeight");
static auto leftField = javaNode->getClass()->getField<jfloat>("mLeft");
static auto topField = javaNode->getClass()->getField<jfloat>("mTop");
javaNode->setFieldValue(widthField, CSSNodeLayoutGetWidth(root));
javaNode->setFieldValue(heightField, CSSNodeLayoutGetHeight(root));
javaNode->setFieldValue(leftField, CSSNodeLayoutGetLeft(root));
javaNode->setFieldValue(topField, CSSNodeLayoutGetTop(root));
_jniTransferLayoutDirection(root, javaNode);
for (uint32_t i = 0; i < CSSNodeChildCount(root); i++) {
_jniTransferLayoutOutputsRecursive(CSSNodeGetChild(root, i));
}
}
static void _jniPrint(CSSNodeRef node) {
auto obj = adopt_local(Environment::current()->NewLocalRef(reinterpret_cast<jweak>(CSSNodeGetContext(node))));
cout << obj->toString() << endl;
@@ -25,8 +50,11 @@ static CSSSize _jniMeasureFunc(CSSNodeRef node,
float height,
CSSMeasureMode heightMode) {
auto obj = adopt_local(Environment::current()->NewLocalRef(reinterpret_cast<jweak>(CSSNodeGetContext(node))));
static auto measureFunc =
obj->getClass()->getMethod<jlong(jfloat, jint, jfloat, jint)>("measure");
_jniTransferLayoutDirection(node, obj);
const auto measureResult = measureFunc(obj, width, widthMode, height, heightMode);
static_assert(sizeof(measureResult) == 8,
@@ -79,10 +107,12 @@ void jni_CSSNodeRemoveChild(alias_ref<jobject>, jlong nativePointer, jlong child
}
void jni_CSSNodeCalculateLayout(alias_ref<jobject>, jlong nativePointer) {
CSSNodeCalculateLayout(_jlong2CSSNodeRef(nativePointer),
const CSSNodeRef root = _jlong2CSSNodeRef(nativePointer);
CSSNodeCalculateLayout(root,
CSSUndefined,
CSSUndefined,
CSSNodeStyleGetDirection(_jlong2CSSNodeRef(nativePointer)));
_jniTransferLayoutOutputsRecursive(root);
}
void jni_CSSNodeMarkDirty(alias_ref<jobject>, jlong nativePointer) {
@@ -139,11 +169,6 @@ void jni_CSSNodeMarkLayoutSeen(alias_ref<jobject>, jlong nativePointer) {
static_cast<type>(value)); \
}
#define CSS_NODE_JNI_LAYOUT_PROP(javatype, type, name) \
javatype jni_CSSNodeLayoutGet##name(alias_ref<jobject>, jlong nativePointer) { \
return (javatype) CSSNodeLayoutGet##name(_jlong2CSSNodeRef(nativePointer)); \
}
CSS_NODE_JNI_STYLE_PROP(jint, CSSDirection, Direction);
CSS_NODE_JNI_STYLE_PROP(jint, CSSFlexDirection, FlexDirection);
CSS_NODE_JNI_STYLE_PROP(jint, CSSJustify, JustifyContent);
@@ -173,12 +198,6 @@ CSS_NODE_JNI_STYLE_PROP(jfloat, float, Height);
CSS_NODE_JNI_STYLE_PROP(jfloat, float, MinHeight);
CSS_NODE_JNI_STYLE_PROP(jfloat, float, MaxHeight);
CSS_NODE_JNI_LAYOUT_PROP(jfloat, float, Width);
CSS_NODE_JNI_LAYOUT_PROP(jfloat, float, Height);
CSS_NODE_JNI_LAYOUT_PROP(jfloat, float, Left);
CSS_NODE_JNI_LAYOUT_PROP(jfloat, float, Top);
CSS_NODE_JNI_LAYOUT_PROP(jint, CSSDirection, Direction);
#define CSSMakeNativeMethod(name) makeNativeMethod(#name, name)
jint JNI_OnLoad(JavaVM *vm, void *) {
@@ -244,12 +263,6 @@ jint JNI_OnLoad(JavaVM *vm, void *) {
CSSMakeNativeMethod(jni_CSSNodeStyleGetMaxHeight),
CSSMakeNativeMethod(jni_CSSNodeStyleSetMaxHeight),
CSSMakeNativeMethod(jni_CSSNodeLayoutGetLeft),
CSSMakeNativeMethod(jni_CSSNodeLayoutGetTop),
CSSMakeNativeMethod(jni_CSSNodeLayoutGetWidth),
CSSMakeNativeMethod(jni_CSSNodeLayoutGetHeight),
CSSMakeNativeMethod(jni_CSSNodeLayoutGetDirection),
CSSMakeNativeMethod(jni_CSSNodeGetInstanceCount),
});
});