private void measureChildNode(int widthMeasureSpec, int heightMeasureSpec) { int childNodeViewsCount = mChildNodeViews.size(); for (int i = 0; i < childNodeViewsCount; i++) { UDView nodeView = mChildNodeViews.get(i); View view = nodeView.getView(); CSSNode node = nodeView.getCssNode(); if (node.getSizeToFit()) { int margins = (int) (node.getMargin().get(Spacing.LEFT) + node.getMargin().get(Spacing.RIGHT)); measureChild(view, widthMeasureSpec - margins, heightMeasureSpec); node.setNoDirtyStyleWidth(view.getMeasuredWidth()); node.setNoDirtyStyleHeight(view.getMeasuredHeight()); } if (view instanceof LVViewGroup) { LVViewGroup viewGroup = (LVViewGroup) view; if (viewGroup.getCssNode().getChildCount() > 0) { viewGroup.measureChildNode(widthMeasureSpec, heightMeasureSpec); } } } }
@Override public void setThemedContext(ThemedReactContext themedContext) { super.setThemedContext(themedContext); // TODO #7120264: cache this stuff better mEditText = new EditText(getThemedContext()); // This is needed to fix an android bug since 4.4.3 which will throw an NPE in measure, // setting the layoutParams fixes it: https://code.google.com/p/android/issues/detail?id=75877 mEditText.setLayoutParams( new ViewGroup.LayoutParams( ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT)); setDefaultPadding(Spacing.LEFT, mEditText.getPaddingLeft()); setDefaultPadding(Spacing.TOP, mEditText.getPaddingTop()); setDefaultPadding(Spacing.RIGHT, mEditText.getPaddingRight()); setDefaultPadding(Spacing.BOTTOM, mEditText.getPaddingBottom()); mComputedPadding = spacingToFloatArray(getPadding()); }
@Override public void measure(CSSNode node, float width, float height, MeasureOutput measureOutput) { // measure() should never be called before setThemedContext() EditText editText = Assertions.assertNotNull(mEditText); measureOutput.width = width; editText.setTextSize( TypedValue.COMPLEX_UNIT_PX, mFontSize == UNSET ? (int) Math.ceil(PixelUtil.toPixelFromSP(ViewDefaults.FONT_SIZE_SP)) : mFontSize); mComputedPadding = spacingToFloatArray(getPadding()); editText.setPadding( (int) Math.ceil(getPadding().get(Spacing.LEFT)), (int) Math.ceil(getPadding().get(Spacing.TOP)), (int) Math.ceil(getPadding().get(Spacing.RIGHT)), (int) Math.ceil(getPadding().get(Spacing.BOTTOM))); if (mNumberOfLines != UNSET) { editText.setLines(mNumberOfLines); } editText.measure(0 /* unspecified */, 0 /* unspecified */); measureOutput.height = editText.getMeasuredHeight(); }
@Override public void measure(CSSNode node, float width, float height, MeasureOutput measureOutput) { // measure() should never be called before setThemedContext() EditText editText = Assertions.assertNotNull(mEditText); measureOutput.width = width; editText.setTextSize( TypedValue.COMPLEX_UNIT_PX, mFontSize == UNSET ? (int) Math.ceil(PixelUtil.toPixelFromSP(ViewDefaults.FONT_SIZE_SP)) : mFontSize); mComputedPadding = spacingToFloatArray(getPadding()); editText.setPadding( (int) Math.ceil(getPadding().get(Spacing.LEFT)), (int) Math.ceil(getPadding().get(Spacing.TOP)), (int) Math.ceil(getPadding().get(Spacing.RIGHT)), (int) Math.ceil(getPadding().get(Spacing.BOTTOM))); if (mNumberOfLines != UNSET) { editText.setLines(mNumberOfLines); } editText.measure(MEASURE_SPEC, MEASURE_SPEC); measureOutput.height = editText.getMeasuredHeight(); }
@Override public void setThemedContext(ThemedReactContext themedContext) { super.setThemedContext(themedContext); // TODO #7120264: cache this stuff better mEditText = new EditText(getThemedContext()); // This is needed to fix an android bug since 4.4.3 which will throw an NPE in measure, // setting the layoutParams fixes it: https://code.google.com/p/android/issues/detail?id=75877 mEditText.setLayoutParams( new ViewGroup.LayoutParams( ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT)); setDefaultPadding(Spacing.START, mEditText.getPaddingStart()); setDefaultPadding(Spacing.TOP, mEditText.getPaddingTop()); setDefaultPadding(Spacing.END, mEditText.getPaddingEnd()); setDefaultPadding(Spacing.BOTTOM, mEditText.getPaddingBottom()); mComputedPadding = new float[] { getPadding(Spacing.START), getPadding(Spacing.TOP), getPadding(Spacing.END), getPadding(Spacing.BOTTOM), }; }
@Override public void onCollectExtraUpdates(UIViewOperationQueue uiViewOperationQueue) { if (mIsVirtual) { return; } super.onCollectExtraUpdates(uiViewOperationQueue); if (mPreparedSpannableText != null) { ReactTextUpdate reactTextUpdate = new ReactTextUpdate( mPreparedSpannableText, UNSET, mContainsImages, getPadding(Spacing.START), getPadding(Spacing.TOP), getPadding(Spacing.END), getPadding(Spacing.BOTTOM), getTextAlign() ); uiViewOperationQueue.enqueueUpdateExtraData(getReactTag(), reactTextUpdate); } }
private static void setMargin() { String margin = mInlineMap.get(MARGIN); if (margin != null) { Float fMargin = pixelFloat(margin); mNode.setMargin(Spacing.LEFT, fMargin); mNode.setMargin(Spacing.TOP, fMargin); mNode.setMargin(Spacing.BOTTOM, fMargin); mNode.setMargin(Spacing.RIGHT, fMargin); } String marginLeft = mInlineMap.get(MARGINLEFT); if (marginLeft != null) { mNode.setMargin(Spacing.LEFT, pixelFloat(marginLeft)); } String marginTop = mInlineMap.get(MARGINTOP); if (marginTop != null) { mNode.setMargin(Spacing.TOP, pixelFloat(marginTop)); } String marginBottom = mInlineMap.get(MARGINBOTTOM); if (marginBottom != null) { mNode.setMargin(Spacing.BOTTOM, pixelFloat(marginBottom)); } String marginRight = mInlineMap.get(MARGINRIGHT); if (marginRight != null) { mNode.setMargin(Spacing.RIGHT, pixelFloat(marginRight)); } }
private static void setPadding() { String padding = mInlineMap.get(PADDING); if (padding != null) { Float mPadding = pixelFloat(padding); mNode.setPadding(Spacing.LEFT, mPadding); mNode.setPadding(Spacing.TOP, mPadding); mNode.setPadding(Spacing.BOTTOM, mPadding); mNode.setPadding(Spacing.RIGHT, mPadding); } String paddingLeft = mInlineMap.get(PADDINGLEFT); if (paddingLeft != null) { mNode.setPadding(Spacing.LEFT, pixelFloat(paddingLeft)); } String paddingTop = mInlineMap.get(PADDINGTOP); if (paddingTop != null) { mNode.setPadding(Spacing.TOP, pixelFloat(paddingTop)); } String paddingBottom = mInlineMap.get(PADDINGBOTTOM); if (paddingBottom != null) { mNode.setPadding(Spacing.BOTTOM, pixelFloat(paddingBottom)); } String paddingRight = mInlineMap.get(PADDINGRIGHT); if (paddingRight != null) { mNode.setPadding(Spacing.RIGHT, pixelFloat(paddingRight)); } }
private static float[] spacingToFloatArray(Spacing spacing) { return new float[] { spacing.get(Spacing.LEFT), spacing.get(Spacing.TOP), spacing.get(Spacing.RIGHT), spacing.get(Spacing.BOTTOM), }; }
@Override public void measure( CSSNode node, float width, CSSMeasureMode widthMode, float height, CSSMeasureMode heightMode, MeasureOutput measureOutput) { // measure() should never be called before setThemedContext() EditText editText = Assertions.assertNotNull(mEditText); measureOutput.width = widthMode == CSSMeasureMode.UNDEFINED ? CSSConstants.UNDEFINED : width; editText.setTextSize( TypedValue.COMPLEX_UNIT_PX, mFontSize == UNSET ? (int) Math.ceil(PixelUtil.toPixelFromSP(ViewDefaults.FONT_SIZE_SP)) : mFontSize); mComputedPadding = spacingToFloatArray(getPadding()); editText.setPadding( (int) Math.ceil(getPadding().get(Spacing.LEFT)), (int) Math.ceil(getPadding().get(Spacing.TOP)), (int) Math.ceil(getPadding().get(Spacing.RIGHT)), (int) Math.ceil(getPadding().get(Spacing.BOTTOM))); if (mNumberOfLines != UNSET) { editText.setLines(mNumberOfLines); } editText.measure(0 /* unspecified */, 0 /* unspecified */); measureOutput.height = editText.getMeasuredHeight(); }
@Override public void measure( CSSNodeAPI node, float width, CSSMeasureMode widthMode, float height, CSSMeasureMode heightMode, MeasureOutput measureOutput) { // measure() should never be called before setThemedContext() EditText editText = Assertions.assertNotNull(mEditText); editText.setTextSize( TypedValue.COMPLEX_UNIT_PX, mFontSize == UNSET ? (int) Math.ceil(PixelUtil.toPixelFromSP(ViewDefaults.FONT_SIZE_SP)) : mFontSize); mComputedPadding = new float[] { getPadding(Spacing.START), getPadding(Spacing.TOP), getPadding(Spacing.END), getPadding(Spacing.BOTTOM), }; editText.setPadding( (int) Math.floor(getPadding(Spacing.START)), (int) Math.floor(getPadding(Spacing.TOP)), (int) Math.floor(getPadding(Spacing.END)), (int) Math.floor(getPadding(Spacing.BOTTOM))); if (mNumberOfLines != UNSET) { editText.setLines(mNumberOfLines); } editText.measure( MeasureUtil.getMeasureSpec(width, widthMode), MeasureUtil.getMeasureSpec(height, heightMode)); measureOutput.width = editText.getMeasuredWidth(); measureOutput.height = editText.getMeasuredHeight(); }
@Override public void onCollectExtraUpdates(UIViewOperationQueue uiViewOperationQueue) { super.onCollectExtraUpdates(uiViewOperationQueue); if (mComputedPadding != null) { float[] updatedPadding = mComputedPadding; if (getLayoutDirection() == CSSDirection.RTL) { updatedPadding = new float[] { getPadding(Spacing.END), getPadding(Spacing.TOP), getPadding(Spacing.START), getPadding(Spacing.BOTTOM), }; } uiViewOperationQueue.enqueueUpdateExtraData(getReactTag(), updatedPadding); mComputedPadding = null; } if (mJsEventCount != UNSET) { Spannable preparedSpannableText = fromTextCSSNode(this); ReactTextUpdate reactTextUpdate = new ReactTextUpdate( preparedSpannableText, mJsEventCount, mContainsImages, getPadding(Spacing.START), getPadding(Spacing.TOP), getPadding(Spacing.END), getPadding(Spacing.BOTTOM), mTextAlign ); uiViewOperationQueue.enqueueUpdateExtraData(getReactTag(), reactTextUpdate); } }
@Override public void setPadding(int spacingType, float padding) { super.setPadding(spacingType, padding); mComputedPadding = new float[] { getPadding(Spacing.START), getPadding(Spacing.TOP), getPadding(Spacing.END), getPadding(Spacing.BOTTOM), }; markUpdated(); }
/** * We use this method for getting color for rounded borders only similarly as for * {@link #getFullBorderWidth}. */ private int getFullBorderColor() { float rgb = (mBorderRGB != null && !CSSConstants.isUndefined(mBorderRGB.getRaw(Spacing.ALL))) ? mBorderRGB.getRaw(Spacing.ALL) : DEFAULT_BORDER_RGB; float alpha = (mBorderAlpha != null && !CSSConstants.isUndefined(mBorderAlpha.getRaw(Spacing.ALL))) ? mBorderAlpha.getRaw(Spacing.ALL) : DEFAULT_BORDER_ALPHA; return ReactViewBackgroundDrawable.colorFromAlphaAndRGBComponents(alpha, rgb); }
private void updatePadding() { for (int spacingType = Spacing.LEFT; spacingType <= Spacing.ALL; spacingType++) { if (spacingType == Spacing.LEFT || spacingType == Spacing.RIGHT || spacingType == Spacing.START || spacingType == Spacing.END) { if (CSSConstants.isUndefined(mPadding.getRaw(spacingType)) && CSSConstants.isUndefined(mPadding.getRaw(Spacing.HORIZONTAL)) && CSSConstants.isUndefined(mPadding.getRaw(Spacing.ALL))) { super.setPadding(spacingType, mDefaultPadding.getRaw(spacingType)); } else { super.setPadding(spacingType, mPadding.getRaw(spacingType)); } } else if (spacingType == Spacing.TOP || spacingType == Spacing.BOTTOM) { if (CSSConstants.isUndefined(mPadding.getRaw(spacingType)) && CSSConstants.isUndefined(mPadding.getRaw(Spacing.VERTICAL)) && CSSConstants.isUndefined(mPadding.getRaw(Spacing.ALL))) { super.setPadding(spacingType, mDefaultPadding.getRaw(spacingType)); } else { super.setPadding(spacingType, mPadding.getRaw(spacingType)); } } else { if (CSSConstants.isUndefined(mPadding.getRaw(spacingType))) { super.setPadding(spacingType, mDefaultPadding.getRaw(spacingType)); } else { super.setPadding(spacingType, mPadding.getRaw(spacingType)); } } } }
@Test public void testDimensions() { LayoutShadowNode reactShadowNode = spy(new LayoutShadowNode()); ReactStylesDiffMap map = spy( buildStyles( "width", 10.0, "height", 10.0, "left", 10.0, "top", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setStyleWidth(anyFloat()); verify(map).getFloat(eq("width"), anyFloat()); verify(reactShadowNode).setStyleHeight(anyFloat()); verify(map).getFloat(eq("height"), anyFloat()); verify(reactShadowNode).setPosition(eq(Spacing.START), anyFloat()); verify(map).getFloat(eq("left"), anyFloat()); verify(reactShadowNode).setPosition(eq(Spacing.TOP), anyFloat()); verify(map).getFloat(eq("top"), anyFloat()); reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles()); reactShadowNode.updateProperties(map); verify(reactShadowNode, never()).setStyleWidth(anyFloat()); verify(map, never()).getFloat(eq("width"), anyFloat()); verify(reactShadowNode, never()).setStyleHeight(anyFloat()); verify(map, never()).getFloat(eq("height"), anyFloat()); verify(reactShadowNode, never()).setPosition(eq(Spacing.START), anyFloat()); verify(map, never()).getFloat(eq("left"), anyFloat()); verify(reactShadowNode, never()).setPosition(eq(Spacing.TOP), anyFloat()); verify(map, never()).getFloat(eq("top"), anyFloat()); }
@Test public void testPosition() { LayoutShadowNode reactShadowNode = spy(new LayoutShadowNode()); ReactStylesDiffMap map = spy(buildStyles( "position", "absolute", "bottom", 10.0, "right", 5.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPosition(eq(Spacing.BOTTOM), anyFloat()); verify(reactShadowNode).setPosition(eq(Spacing.END), anyFloat()); verify(reactShadowNode).setPositionType(any(CSSPositionType.class)); verify(map).getFloat("bottom", Float.NaN); verify(map).getFloat("right", Float.NaN); reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles()); reactShadowNode.updateProperties(map); verify(reactShadowNode, never()).setPosition(eq(Spacing.BOTTOM), anyFloat()); verify(reactShadowNode, never()).setPosition(eq(Spacing.END), anyFloat()); verify(reactShadowNode, never()).setPositionType(any(CSSPositionType.class)); verify(map, never()).getFloat("bottom", Float.NaN); verify(map, never()).getFloat("right", Float.NaN); }
public void clear() { style.direction = CSSDirection.INHERIT; style.flexDirection = CSSFlexDirection.COLUMN; style.justifyContent = CSSJustify.FLEX_START; style.alignContent = CSSAlign.FLEX_START; style.alignItems = CSSAlign.STRETCH; style.alignSelf = CSSAlign.AUTO; style.positionType = CSSPositionType.RELATIVE; style.flexWrap = CSSWrap.NOWRAP; style.flex = 0; style.margin = new Spacing(); style.padding = new Spacing(); style.border = new Spacing(); style.positionTop = CSSConstants.UNDEFINED; style.positionBottom = CSSConstants.UNDEFINED; style.positionLeft = CSSConstants.UNDEFINED; style.positionRight = CSSConstants.UNDEFINED; style.width = CSSConstants.UNDEFINED; style.height = CSSConstants.UNDEFINED; style.minWidth = CSSConstants.UNDEFINED; style.minHeight = CSSConstants.UNDEFINED; style.maxWidth = CSSConstants.UNDEFINED; style.maxHeight = CSSConstants.UNDEFINED; }
void fillCSSNode(CSSNode node) { if (width != WRAP_CONTENT && width != MATCH_PARENT) { node.setStyleWidth(width); } else { node.setStyleWidth(CSSConstants.UNDEFINED); } if (height != WRAP_CONTENT && height != MATCH_PARENT) { node.setStyleHeight(height); } else { node.setStyleHeight(CSSConstants.UNDEFINED); } node.setMinWidth(minWidth); node.setMinHeight(minHeight); node.setMaxWidth(maxWidth); node.setMaxHeight(maxHeight); node.setPositionLeft(left); node.setPositionRight(right); node.setPositionTop(top); node.setPositionBottom(bottom); node.setMargin(Spacing.ALL, margin); node.setMargin(Spacing.LEFT, marginLeft); node.setMargin(Spacing.RIGHT, marginRight); node.setMargin(Spacing.TOP, marginTop); node.setMargin(Spacing.BOTTOM, marginBottom); node.setAlignSelf(alignSelf); node.setFlex(flex); node.setPositionType(position); }
private void updatePath() { if (!mNeedUpdatePathForBorderRadius) { return; } mNeedUpdatePathForBorderRadius = false; if (mPathForBorderRadius == null) { mPathForBorderRadius = new Path(); mTempRectForBorderRadius = new RectF(); mPathForBorderRadiusOutline = new Path(); mTempRectForBorderRadiusOutline = new RectF(); } mPathForBorderRadius.reset(); mPathForBorderRadiusOutline.reset(); mTempRectForBorderRadius.set(getBounds()); mTempRectForBorderRadiusOutline.set(getBounds()); float fullBorderWidth = getFullBorderWidth(); if (fullBorderWidth > 0) { mTempRectForBorderRadius.inset(fullBorderWidth * 0.5f, fullBorderWidth * 0.5f); } float defaultBorderRadius = !CSSConstants.isUndefined(mBorderRadius) ? mBorderRadius : 0; float topLeftRadius = mBorderCornerRadii != null && !CSSConstants.isUndefined(mBorderCornerRadii[0]) ? mBorderCornerRadii[0] : defaultBorderRadius; float topRightRadius = mBorderCornerRadii != null && !CSSConstants.isUndefined(mBorderCornerRadii[1]) ? mBorderCornerRadii[1] : defaultBorderRadius; float bottomRightRadius = mBorderCornerRadii != null && !CSSConstants.isUndefined(mBorderCornerRadii[2]) ? mBorderCornerRadii[2] : defaultBorderRadius; float bottomLeftRadius = mBorderCornerRadii != null && !CSSConstants.isUndefined(mBorderCornerRadii[3]) ? mBorderCornerRadii[3] : defaultBorderRadius; mPathForBorderRadius.addRoundRect( mTempRectForBorderRadius, new float[] { topLeftRadius, topLeftRadius, topRightRadius, topRightRadius, bottomRightRadius, bottomRightRadius, bottomLeftRadius, bottomLeftRadius }, Path.Direction.CW); float extraRadiusForOutline = 0; if (mBorderWidth != null) { extraRadiusForOutline = mBorderWidth.get(Spacing.ALL) / 2f; } mPathForBorderRadiusOutline.addRoundRect( mTempRectForBorderRadiusOutline, new float[] { topLeftRadius + extraRadiusForOutline, topLeftRadius + extraRadiusForOutline, topRightRadius + extraRadiusForOutline, topRightRadius + extraRadiusForOutline, bottomRightRadius + extraRadiusForOutline, bottomRightRadius + extraRadiusForOutline, bottomLeftRadius + extraRadiusForOutline, bottomLeftRadius + extraRadiusForOutline }, Path.Direction.CW); mPathEffectForBorderStyle = mBorderStyle != null ? mBorderStyle.getPathEffect(getFullBorderWidth()) : null; }
/** * For rounded borders we use default "borderWidth" property. */ private float getFullBorderWidth() { return (mBorderWidth != null && !CSSConstants.isUndefined(mBorderWidth.getRaw(Spacing.ALL))) ? mBorderWidth.getRaw(Spacing.ALL) : 0f; }
/** * We use this method for getting color for rounded borders only similarly as for * {@link #getFullBorderWidth}. */ private int getFullBorderColor() { return (mBorderColor != null && !CSSConstants.isUndefined(mBorderColor.getRaw(Spacing.ALL))) ? (int) (long) mBorderColor.getRaw(Spacing.ALL) : DEFAULT_BORDER_COLOR; }
@Test public void testMargin() { // margin LayoutShadowNode reactShadowNode = spy(new LayoutShadowNode()); ReactStylesDiffMap map = spy(buildStyles("margin", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.ALL), anyFloat()); verify(map).getFloat("margin", CSSConstants.UNDEFINED); // marginVertical reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("marginVertical", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.VERTICAL), anyFloat()); verify(map).getFloat("marginVertical", CSSConstants.UNDEFINED); // marginHorizontal reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("marginHorizontal", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.HORIZONTAL), anyFloat()); verify(map).getFloat("marginHorizontal", CSSConstants.UNDEFINED); // marginTop reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("marginTop", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.TOP), anyFloat()); verify(map).getFloat("marginTop", CSSConstants.UNDEFINED); // marginBottom reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("marginBottom", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.BOTTOM), anyFloat()); verify(map).getFloat("marginBottom", CSSConstants.UNDEFINED); // marginLeft reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("marginLeft", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.LEFT), anyFloat()); verify(map).getFloat("marginLeft", CSSConstants.UNDEFINED); // marginRight reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("marginRight", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setMargin(eq(Spacing.RIGHT), anyFloat()); verify(map).getFloat("marginRight", CSSConstants.UNDEFINED); // no margin reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles()); reactShadowNode.updateProperties(map); verify(reactShadowNode, never()).setMargin(anyInt(), anyFloat()); verify(map, never()).getFloat("margin", CSSConstants.UNDEFINED); }
@Test public void testPadding() { // padding LayoutShadowNode reactShadowNode = spy(new LayoutShadowNode()); ReactStylesDiffMap map = spy(buildStyles("padding", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.ALL), anyFloat()); verify(map).getFloat("padding", CSSConstants.UNDEFINED); // paddingVertical reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("paddingVertical", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.VERTICAL), anyFloat()); verify(map).getFloat("paddingVertical", CSSConstants.UNDEFINED); // paddingHorizontal reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("paddingHorizontal", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.HORIZONTAL), anyFloat()); verify(map).getFloat("paddingHorizontal", CSSConstants.UNDEFINED); // paddingTop reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("paddingTop", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.TOP), anyFloat()); verify(map).getFloat("paddingTop", CSSConstants.UNDEFINED); // paddingBottom reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("paddingBottom", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.BOTTOM), anyFloat()); verify(map).getFloat("paddingBottom", CSSConstants.UNDEFINED); // paddingLeft reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("paddingLeft", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.LEFT), anyFloat()); verify(map).getFloat("paddingLeft", CSSConstants.UNDEFINED); // paddingRight reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles("paddingRight", 10.0)); reactShadowNode.updateProperties(map); verify(reactShadowNode).setPadding(eq(Spacing.RIGHT), anyFloat()); verify(map).getFloat("paddingRight", CSSConstants.UNDEFINED); // no padding reactShadowNode = spy(new LayoutShadowNode()); map = spy(buildStyles()); reactShadowNode.updateProperties(map); verify(reactShadowNode, never()).setPadding(anyInt(), anyFloat()); verify(map, never()).getFloat("padding", CSSConstants.UNDEFINED); }
@Test public void testPropertiesResetToDefault() { DisplayMetrics displayMetrics = new DisplayMetrics(); displayMetrics.density = 1.0f; DisplayMetricsHolder.setWindowDisplayMetrics(displayMetrics); LayoutShadowNode reactShadowNode = spy(new LayoutShadowNode()); ReactStylesDiffMap map = buildStyles( "width", 10.0, "height", 10.0, "left", 10.0, "top", 10.0, "flex", 1.0, "padding", 10.0, "marginLeft", 10.0, "borderTopWidth", 10.0, "flexDirection", "row", "alignSelf", "stretch", "alignItems", "center", "justifyContent", "space_between", "position", "absolute"); reactShadowNode.updateProperties(map); verify(reactShadowNode).setStyleWidth(10.f); verify(reactShadowNode).setStyleHeight(10.f); verify(reactShadowNode).setPositionLeft(10.f); verify(reactShadowNode).setPositionTop(10.f); verify(reactShadowNode).setFlex(1.0f); verify(reactShadowNode).setPadding(Spacing.ALL, 10.f); verify(reactShadowNode).setMargin(Spacing.LEFT, 10.f); verify(reactShadowNode).setBorder(Spacing.TOP, 10.f); verify(reactShadowNode).setFlexDirection(CSSFlexDirection.ROW); verify(reactShadowNode).setAlignSelf(CSSAlign.STRETCH); verify(reactShadowNode).setAlignItems(CSSAlign.CENTER); verify(reactShadowNode).setJustifyContent(CSSJustify.SPACE_BETWEEN); verify(reactShadowNode).setPositionType(CSSPositionType.ABSOLUTE); map = buildStyles( "width", null, "height", null, "left", null, "top", null, "flex", null, "padding", null, "marginLeft", null, "borderTopWidth", null, "flexDirection", null, "alignSelf", null, "alignItems", null, "justifyContent", null, "position", null); reset(reactShadowNode); reactShadowNode.updateProperties(map); verify(reactShadowNode).setStyleWidth(CSSConstants.UNDEFINED); verify(reactShadowNode).setStyleHeight(CSSConstants.UNDEFINED); verify(reactShadowNode).setPositionLeft(CSSConstants.UNDEFINED); verify(reactShadowNode).setPositionTop(CSSConstants.UNDEFINED); verify(reactShadowNode).setFlex(0.f); verify(reactShadowNode).setPadding(Spacing.ALL, CSSConstants.UNDEFINED); verify(reactShadowNode).setMargin(Spacing.LEFT, CSSConstants.UNDEFINED); verify(reactShadowNode).setBorder(Spacing.TOP, CSSConstants.UNDEFINED); verify(reactShadowNode).setFlexDirection(CSSFlexDirection.COLUMN); verify(reactShadowNode).setAlignSelf(CSSAlign.AUTO); verify(reactShadowNode).setAlignItems(CSSAlign.STRETCH); verify(reactShadowNode).setJustifyContent(CSSJustify.FLEX_START); verify(reactShadowNode).setPositionType(CSSPositionType.RELATIVE); }
@Test public void testSettingDefaultStyleValues() { mockStatic(PixelUtil.class); when(PixelUtil.toPixelFromDIP(anyFloat())).thenAnswer( new Answer() { @Override public Float answer(InvocationOnMock invocation) throws Throwable { Object[] args = invocation.getArguments(); return (Float) args[0]; } }); LayoutShadowNode[] nodes = new LayoutShadowNode[7]; for (int idx = 0; idx < nodes.length; idx++) { nodes[idx] = new LayoutShadowNode(); nodes[idx].setDefaultPadding(Spacing.LEFT, 15); nodes[idx].setDefaultPadding(Spacing.TOP, 25); nodes[idx].setDefaultPadding(Spacing.RIGHT, 35); nodes[idx].setDefaultPadding(Spacing.BOTTOM, 45); } ReactStylesDiffMap[] mapNodes = new ReactStylesDiffMap[7]; mapNodes[0] = buildStyles("paddingLeft", 10.0, "paddingHorizontal", 5.0); mapNodes[1] = buildStyles("padding", 10.0, "paddingTop", 5.0); mapNodes[2] = buildStyles("paddingLeft", 10.0, "paddingVertical", 5.0); mapNodes[3] = buildStyles("paddingBottom", 10.0, "paddingHorizontal", 5.0); mapNodes[4] = buildStyles("padding", null, "paddingTop", 5.0); mapNodes[5] = buildStyles( "paddingRight", 10.0, "paddingHorizontal", null, "paddingVertical", 7.0); mapNodes[6] = buildStyles("margin", 5.0); for (int idx = 0; idx < nodes.length; idx++) { nodes[idx].updateProperties(mapNodes[idx]); } assertEquals(10.0, nodes[0].getPadding().get(Spacing.LEFT), .0001); assertEquals(25.0, nodes[0].getPadding().get(Spacing.TOP), .0001); assertEquals(5.0, nodes[0].getPadding().get(Spacing.RIGHT), .0001); assertEquals(45.0, nodes[0].getPadding().get(Spacing.BOTTOM), .0001); assertEquals(10.0, nodes[1].getPadding().get(Spacing.LEFT), .0001); assertEquals(5.0, nodes[1].getPadding().get(Spacing.TOP), .0001); assertEquals(10.0, nodes[1].getPadding().get(Spacing.RIGHT), .0001); assertEquals(10.0, nodes[1].getPadding().get(Spacing.BOTTOM), .0001); assertEquals(10.0, nodes[2].getPadding().get(Spacing.LEFT), .0001); assertEquals(5.0, nodes[2].getPadding().get(Spacing.TOP), .0001); assertEquals(35.0, nodes[2].getPadding().get(Spacing.RIGHT), .0001); assertEquals(5.0, nodes[2].getPadding().get(Spacing.BOTTOM), .0001); assertEquals(5.0, nodes[3].getPadding().get(Spacing.LEFT), .0001); assertEquals(25.0, nodes[3].getPadding().get(Spacing.TOP), .0001); assertEquals(5.0, nodes[3].getPadding().get(Spacing.RIGHT), .0001); assertEquals(10.0, nodes[3].getPadding().get(Spacing.BOTTOM), .0001); assertEquals(15.0, nodes[4].getPadding().get(Spacing.LEFT), .0001); assertEquals(5.0, nodes[4].getPadding().get(Spacing.TOP), .0001); assertEquals(35.0, nodes[4].getPadding().get(Spacing.RIGHT), .0001); assertEquals(45.0, nodes[4].getPadding().get(Spacing.BOTTOM), .0001); assertEquals(15.0, nodes[5].getPadding().get(Spacing.LEFT), .0001); assertEquals(7.0, nodes[5].getPadding().get(Spacing.TOP), .0001); assertEquals(10.0, nodes[5].getPadding().get(Spacing.RIGHT), .0001); assertEquals(7.0, nodes[5].getPadding().get(Spacing.BOTTOM), .0001); assertEquals(15.0, nodes[6].getPadding().get(Spacing.LEFT), .0001); assertEquals(25.0, nodes[6].getPadding().get(Spacing.TOP), .0001); assertEquals(35.0, nodes[6].getPadding().get(Spacing.RIGHT), .0001); assertEquals(45.0, nodes[6].getPadding().get(Spacing.BOTTOM), .0001); }