Implement java bindings for custom baseline function

Summary: Implement java bindings for custom baseline function

Differential Revision: D4392516

fbshipit-source-id: 39cf6066f8e5982268becd87e54c9ab51fbf7a90
This commit is contained in:
Emil Sjolander
2017-01-10 07:03:56 -08:00
committed by Facebook Github Bot
parent 1782646723
commit c04604dbc0
5 changed files with 78 additions and 0 deletions

View File

@@ -0,0 +1,22 @@
/**
* Copyright (c) 2014-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
package com.facebook.yoga;
import com.facebook.proguard.annotations.DoNotStrip;
@DoNotStrip
public interface YogaBaselineFunction {
/**
* Return the baseline of the node in pixels. When no baseline function is set the baseline
* default to the computed height of the node.
*/
@DoNotStrip
float baseline(YogaNodeAPI node, float width, float height);
}

View File

@@ -52,6 +52,7 @@ public class YogaNode implements YogaNodeAPI<YogaNode> {
private YogaNode mParent; private YogaNode mParent;
private List<YogaNode> mChildren; private List<YogaNode> mChildren;
private YogaMeasureFunction mMeasureFunction; private YogaMeasureFunction mMeasureFunction;
private YogaBaselineFunction mBaselineFunction;
private long mNativePointer; private long mNativePointer;
private Object mData; private Object mData;
@@ -623,6 +624,18 @@ public class YogaNode implements YogaNodeAPI<YogaNode> {
YogaMeasureMode.values()[heightMode]); YogaMeasureMode.values()[heightMode]);
} }
private native void jni_YGNodeSetHasBaselineFunc(long nativePointer, boolean hasMeasureFunc);
@Override
public void setBaselineFunction(YogaBaselineFunction baselineFunction) {
mBaselineFunction = baselineFunction;
jni_YGNodeSetHasBaselineFunc(mNativePointer, baselineFunction != null);
}
@DoNotStrip
public final float baseline(float width, float height) {
return mBaselineFunction.baseline(this, width, height);
}
@Override @Override
public boolean isMeasureDefined() { public boolean isMeasureDefined() {
return mMeasureFunction != null; return mMeasureFunction != null;

View File

@@ -18,6 +18,7 @@ public interface YogaNodeAPI<YogaNodeType extends YogaNodeAPI> {
YogaNodeType getParent(); YogaNodeType getParent();
int indexOf(YogaNodeType child); int indexOf(YogaNodeType child);
void setMeasureFunction(YogaMeasureFunction measureFunction); void setMeasureFunction(YogaMeasureFunction measureFunction);
void setBaselineFunction(YogaBaselineFunction measureFunction);
boolean isMeasureDefined(); boolean isMeasureDefined();
void calculateLayout(); void calculateLayout();
boolean isDirty(); boolean isDirty();

View File

@@ -63,6 +63,14 @@ static void YGPrint(YGNodeRef node) {
} }
} }
static float YGJNIBaselineFunc(YGNodeRef node, float width, float height) {
if (auto obj = YGNodeJobject(node)->lockLocal()) {
return findClassLocal("com/facebook/yoga/YogaNode")->getMethod<jfloat(jfloat, jfloat)>("baseline")(obj, width, height);
} else {
return height;
}
}
static YGSize YGJNIMeasureFunc(YGNodeRef node, static YGSize YGJNIMeasureFunc(YGNodeRef node,
float width, float width,
YGMeasureMode widthMode, YGMeasureMode widthMode,
@@ -203,6 +211,10 @@ void jni_YGNodeSetHasMeasureFunc(alias_ref<jobject>, jlong nativePointer, jboole
YGNodeSetMeasureFunc(_jlong2YGNodeRef(nativePointer), hasMeasureFunc ? YGJNIMeasureFunc : NULL); YGNodeSetMeasureFunc(_jlong2YGNodeRef(nativePointer), hasMeasureFunc ? YGJNIMeasureFunc : NULL);
} }
void jni_YGNodeSetHasBaselineFunc(alias_ref<jobject>, jlong nativePointer, jboolean hasBaselineFunc) {
YGNodeSetBaselineFunc(_jlong2YGNodeRef(nativePointer), hasBaselineFunc ? YGJNIBaselineFunc : NULL);
}
jboolean jni_YGNodeHasNewLayout(alias_ref<jobject>, jlong nativePointer) { jboolean jni_YGNodeHasNewLayout(alias_ref<jobject>, jlong nativePointer) {
return (jboolean) YGNodeGetHasNewLayout(_jlong2YGNodeRef(nativePointer)); return (jboolean) YGNodeGetHasNewLayout(_jlong2YGNodeRef(nativePointer));
} }
@@ -332,6 +344,7 @@ jint JNI_OnLoad(JavaVM *vm, void *) {
YGMakeNativeMethod(jni_YGNodeIsDirty), YGMakeNativeMethod(jni_YGNodeIsDirty),
YGMakeNativeMethod(jni_YGNodeMarkLayoutSeen), YGMakeNativeMethod(jni_YGNodeMarkLayoutSeen),
YGMakeNativeMethod(jni_YGNodeSetHasMeasureFunc), YGMakeNativeMethod(jni_YGNodeSetHasMeasureFunc),
YGMakeNativeMethod(jni_YGNodeSetHasBaselineFunc),
YGMakeNativeMethod(jni_YGNodeCopyStyle), YGMakeNativeMethod(jni_YGNodeCopyStyle),
YGMakeNativeMethod(jni_YGNodeStyleGetDirection), YGMakeNativeMethod(jni_YGNodeStyleGetDirection),
YGMakeNativeMethod(jni_YGNodeStyleSetDirection), YGMakeNativeMethod(jni_YGNodeStyleSetDirection),

View File

@@ -23,6 +23,35 @@ public class YogaNodeTest {
assertEquals(refCount + 1, YogaNode.jni_YGNodeGetInstanceCount()); assertEquals(refCount + 1, YogaNode.jni_YGNodeGetInstanceCount());
} }
@Test
public void testBaseline() {
final YogaNode root = new YogaNode();
root.setFlexDirection(YogaFlexDirection.ROW);
root.setAlignItems(YogaAlign.BASELINE);
root.setWidth(100);
root.setHeight(100);
final YogaNode child1 = new YogaNode();
child1.setWidth(40);
child1.setHeight(40);
root.addChildAt(child1, 0);
final YogaNode child2 = new YogaNode();
child2.setWidth(40);
child2.setHeight(40);
child2.setBaselineFunction(new YogaBaselineFunction() {
public float baseline(YogaNodeAPI node, float width, float height) {
return 0;
}
});
root.addChildAt(child2, 1);
root.calculateLayout();
assertEquals(0, (int) child1.getLayoutY());
assertEquals(40, (int) child2.getLayoutY());
}
@Test @Test
public void testMeasure() { public void testMeasure() {
final YogaNode node = new YogaNode(); final YogaNode node = new YogaNode();