List of usage examples for android.view View getVisibility
@ViewDebug.ExportedProperty(mapping = { @ViewDebug.IntToString(from = VISIBLE, to = "VISIBLE"), @ViewDebug.IntToString(from = INVISIBLE, to = "INVISIBLE"), @ViewDebug.IntToString(from = GONE, to = "GONE") }) @Visibility public int getVisibility()
From source file:beichen.douban.ui.view.LazyViewPager.java
/** * We only want the current page that is being shown to be focusable. *//*w ww . j ava 2 s . c o m*/ @Override public void addFocusables(ArrayList<View> views, int direction, int focusableMode) { final int focusableCount = views.size(); final int descendantFocusability = getDescendantFocusability(); if (descendantFocusability != FOCUS_BLOCK_DESCENDANTS) { for (int i = 0; i < getChildCount(); i++) { final View child = getChildAt(i); if (child.getVisibility() == VISIBLE) { ItemInfo ii = infoForChild(child); if (ii != null && ii.position == mCurItem) { child.addFocusables(views, direction, focusableMode); } } } } // we add ourselves (if focusable) in all cases except for when we are // FOCUS_AFTER_DESCENDANTS and there are some descendants focusable. // this is // to avoid the focus search finding layouts when a more precise search // among the focusable children would be more interesting. if (descendantFocusability != FOCUS_AFTER_DESCENDANTS || // No focusable descendants (focusableCount == views.size())) { // Note that we can't call the superclass here, because it will // add all views in. So we need to do the same thing View does. if (!isFocusable()) { return; } if ((focusableMode & FOCUSABLES_TOUCH_MODE) == FOCUSABLES_TOUCH_MODE && isInTouchMode() && !isFocusableInTouchMode()) { return; } if (views != null) { views.add(this); } } }
From source file:com.devabit.takestock.ui.widget.FlexboxLayout.java
/** * Expand the flex items along the main axis based on the individual flexGrow attribute. * * @param flexLine the flex line to which flex items belong * @param flexDirection the flexDirection value for this FlexboxLayout * @param maxMainSize the maximum main size. Expanded main size will be this size * @param paddingAlongMainAxis the padding value along the main axis * @param startIndex the start index of the children views to be expanded. This index * needs to/*from w w w .j a va2s .c o m*/ * be an absolute index in the flex container (FlexboxLayout), * not the relative index in the flex line. * @return the next index, the next flex line's first flex item starts from the returned index * @see #getFlexDirection() * @see #setFlexDirection(int) * @see LayoutParams#flexGrow */ private int expandFlexItems(FlexLine flexLine, @FlexDirection int flexDirection, int maxMainSize, int paddingAlongMainAxis, int startIndex) { int childIndex = startIndex; if (flexLine.totalFlexGrow <= 0 || maxMainSize < flexLine.mainSize) { childIndex += flexLine.itemCount; return childIndex; } int sizeBeforeExpand = flexLine.mainSize; boolean needsReexpand = false; float unitSpace = (maxMainSize - flexLine.mainSize) / flexLine.totalFlexGrow; flexLine.mainSize = paddingAlongMainAxis; float accumulatedRoundError = 0; for (int i = 0; i < flexLine.itemCount; i++) { View child = getReorderedChildAt(childIndex); if (child == null) { continue; } else if (child.getVisibility() == View.GONE) { childIndex++; continue; } LayoutParams lp = (LayoutParams) child.getLayoutParams(); if (flexDirection == FLEX_DIRECTION_ROW || flexDirection == FLEX_DIRECTION_ROW_REVERSE) { // The direction of the main axis is horizontal if (!mChildrenFrozen[childIndex]) { float rawCalculatedWidth = child.getMeasuredWidth() + unitSpace * lp.flexGrow; if (i == flexLine.itemCount - 1) { rawCalculatedWidth += accumulatedRoundError; accumulatedRoundError = 0; } int newWidth = Math.round(rawCalculatedWidth); if (newWidth > lp.maxWidth) { // This means the child can't expand beyond the value of the maxWidth attribute. // To adjust the flex line length to the size of maxMainSize, remaining // positive free space needs to be re-distributed to other flex items // (children views). In that case, invoke this method again with the same // startIndex. needsReexpand = true; newWidth = lp.maxWidth; mChildrenFrozen[childIndex] = true; flexLine.totalFlexGrow -= lp.flexGrow; } else { accumulatedRoundError += (rawCalculatedWidth - newWidth); if (accumulatedRoundError > 1.0) { newWidth += 1; accumulatedRoundError -= 1.0; } else if (accumulatedRoundError < -1.0) { newWidth -= 1; accumulatedRoundError += 1.0; } } child.measure(MeasureSpec.makeMeasureSpec(newWidth, MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(child.getMeasuredHeight(), MeasureSpec.EXACTLY)); } flexLine.mainSize += child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin; } else { // The direction of the main axis is vertical if (!mChildrenFrozen[childIndex]) { float rawCalculatedHeight = child.getMeasuredHeight() + unitSpace * lp.flexGrow; if (i == flexLine.itemCount - 1) { rawCalculatedHeight += accumulatedRoundError; accumulatedRoundError = 0; } int newHeight = Math.round(rawCalculatedHeight); if (newHeight > lp.maxHeight) { // This means the child can't expand beyond the value of the maxHeight // attribute. // To adjust the flex line length to the size of maxMainSize, remaining // positive free space needs to be re-distributed to other flex items // (children views). In that case, invoke this method again with the same // startIndex. needsReexpand = true; newHeight = lp.maxHeight; mChildrenFrozen[childIndex] = true; flexLine.totalFlexGrow -= lp.flexGrow; } else { accumulatedRoundError += (rawCalculatedHeight - newHeight); if (accumulatedRoundError > 1.0) { newHeight += 1; accumulatedRoundError -= 1.0; } else if (accumulatedRoundError < -1.0) { newHeight -= 1; accumulatedRoundError += 1.0; } } child.measure(MeasureSpec.makeMeasureSpec(child.getMeasuredWidth(), MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(newHeight, MeasureSpec.EXACTLY)); } flexLine.mainSize += child.getMeasuredHeight() + lp.topMargin + lp.bottomMargin; } childIndex++; } if (needsReexpand && sizeBeforeExpand != flexLine.mainSize) { // Re-invoke the method with the same startIndex to distribute the positive free space // that wasn't fully distributed (because of maximum length constraint) expandFlexItems(flexLine, flexDirection, maxMainSize, paddingAlongMainAxis, startIndex); } return childIndex; }
From source file:com.devabit.takestock.ui.widget.FlexboxLayout.java
/** * Sub method for {@link #onLayout(boolean, int, int, int, int)} when the * {@link #mFlexDirection} is either {@link #FLEX_DIRECTION_ROW} or * {@link #FLEX_DIRECTION_ROW_REVERSE}./*from ww w. j ava2 s. c o m*/ * * @param isRtl {@code true} if the horizontal layout direction is right to left, {@code * false} otherwise. * @param left the left position of this View * @param top the top position of this View * @param right the right position of this View * @param bottom the bottom position of this View * @see #getFlexWrap() * @see #setFlexWrap(int) * @see #getJustifyContent() * @see #setJustifyContent(int) * @see #getAlignItems() * @see #setAlignItems(int) * @see LayoutParams#alignSelf */ private void layoutHorizontal(boolean isRtl, int left, int top, int right, int bottom) { int paddingLeft = getPaddingLeft(); int paddingRight = getPaddingRight(); // Use float to reduce the round error that may happen in when justifyContent == // SPACE_BETWEEN or SPACE_AROUND float childLeft; int currentViewIndex = 0; int height = bottom - top; int width = right - left; // childBottom is used if the mFlexWrap is FLEX_WRAP_WRAP_REVERSE otherwise // childTop is used to align the vertical position of the children views. int childBottom = height - getPaddingBottom(); int childTop = getPaddingTop(); // Used only for RTL layout // Use float to reduce the round error that may happen in when justifyContent == // SPACE_BETWEEN or SPACE_AROUND float childRight; for (FlexLine flexLine : mFlexLines) { float spaceBetweenItem = 0f; switch (mJustifyContent) { case JUSTIFY_CONTENT_FLEX_START: childLeft = paddingLeft; childRight = width - paddingRight; break; case JUSTIFY_CONTENT_FLEX_END: childLeft = width - flexLine.mainSize + paddingRight; childRight = flexLine.mainSize - paddingLeft; break; case JUSTIFY_CONTENT_CENTER: childLeft = paddingLeft + (width - flexLine.mainSize) / 2f; childRight = width - paddingRight - (width - flexLine.mainSize) / 2f; break; case JUSTIFY_CONTENT_SPACE_AROUND: if (flexLine.itemCount != 0) { spaceBetweenItem = (width - flexLine.mainSize) / (float) flexLine.itemCount; } childLeft = paddingLeft + spaceBetweenItem / 2f; childRight = width - paddingRight - spaceBetweenItem / 2f; break; case JUSTIFY_CONTENT_SPACE_BETWEEN: childLeft = paddingLeft; float denominator = flexLine.itemCount != 1 ? flexLine.itemCount - 1 : 1f; spaceBetweenItem = (width - flexLine.mainSize) / denominator; childRight = width - paddingRight; break; default: throw new IllegalStateException("Invalid justifyContent is set: " + mJustifyContent); } spaceBetweenItem = Math.max(spaceBetweenItem, 0); for (int i = 0; i < flexLine.itemCount; i++) { View child = getReorderedChildAt(currentViewIndex); if (child == null) { continue; } else if (child.getVisibility() == View.GONE) { currentViewIndex++; continue; } LayoutParams lp = ((LayoutParams) child.getLayoutParams()); childLeft += lp.leftMargin; childRight -= lp.rightMargin; if (mFlexWrap == FLEX_WRAP_WRAP_REVERSE) { if (isRtl) { layoutSingleChildHorizontal(child, flexLine, mFlexWrap, mAlignItems, Math.round(childRight) - child.getMeasuredWidth(), childBottom - child.getMeasuredHeight(), Math.round(childRight), childBottom); } else { layoutSingleChildHorizontal(child, flexLine, mFlexWrap, mAlignItems, Math.round(childLeft), childBottom - child.getMeasuredHeight(), Math.round(childLeft) + child.getMeasuredWidth(), childBottom); } } else { if (isRtl) { layoutSingleChildHorizontal(child, flexLine, mFlexWrap, mAlignItems, Math.round(childRight) - child.getMeasuredWidth(), childTop, Math.round(childRight), childTop + child.getMeasuredHeight()); } else { layoutSingleChildHorizontal(child, flexLine, mFlexWrap, mAlignItems, Math.round(childLeft), childTop, Math.round(childLeft) + child.getMeasuredWidth(), childTop + child.getMeasuredHeight()); } } childLeft += child.getMeasuredWidth() + spaceBetweenItem + lp.rightMargin; childRight -= child.getMeasuredWidth() + spaceBetweenItem + lp.leftMargin; currentViewIndex++; } childTop += flexLine.crossSize; childBottom -= flexLine.crossSize; } }
From source file:com.devabit.takestock.ui.widget.FlexboxLayout.java
/** * Sub method for {@link #onLayout(boolean, int, int, int, int)} when the * {@link #mFlexDirection} is either {@link #FLEX_DIRECTION_COLUMN} or * {@link #FLEX_DIRECTION_COLUMN_REVERSE}. * * @param isRtl {@code true} if the horizontal layout direction is right to left, * {@code false}//from w w w.j a va 2s. co m * otherwise * @param fromBottomToTop {@code true} if the layout direction is bottom to top, {@code false} * otherwise * @param left the left position of this View * @param top the top position of this View * @param right the right position of this View * @param bottom the bottom position of this View * @see #getFlexWrap() * @see #setFlexWrap(int) * @see #getJustifyContent() * @see #setJustifyContent(int) * @see #getAlignItems() * @see #setAlignItems(int) * @see LayoutParams#alignSelf */ private void layoutVertical(boolean isRtl, boolean fromBottomToTop, int left, int top, int right, int bottom) { int paddingTop = getPaddingTop(); int paddingBottom = getPaddingBottom(); int paddingRight = getPaddingRight(); int childLeft = getPaddingLeft(); int currentViewIndex = 0; int width = right - left; int height = bottom - top; // childRight is used if the mFlexWrap is FLEX_WRAP_WRAP_REVERSE otherwise // childLeft is used to align the horizontal position of the children views. int childRight = width - paddingRight; // Use float to reduce the round error that may happen in when justifyContent == // SPACE_BETWEEN or SPACE_AROUND float childTop; // Used only for if the direction is from bottom to top float childBottom; for (FlexLine flexLine : mFlexLines) { float spaceBetweenItem = 0f; switch (mJustifyContent) { case JUSTIFY_CONTENT_FLEX_START: childTop = paddingTop; childBottom = height - paddingBottom; break; case JUSTIFY_CONTENT_FLEX_END: childTop = height - flexLine.mainSize + paddingBottom; childBottom = flexLine.mainSize - paddingTop; break; case JUSTIFY_CONTENT_CENTER: childTop = paddingTop + (height - flexLine.mainSize) / 2f; childBottom = height - paddingBottom - (height - flexLine.mainSize) / 2f; break; case JUSTIFY_CONTENT_SPACE_AROUND: if (flexLine.itemCount != 0) { spaceBetweenItem = (height - flexLine.mainSize) / (float) flexLine.itemCount; } childTop = paddingTop + spaceBetweenItem / 2f; childBottom = height - paddingBottom - spaceBetweenItem / 2f; break; case JUSTIFY_CONTENT_SPACE_BETWEEN: childTop = paddingTop; float denominator = flexLine.itemCount != 1 ? flexLine.itemCount - 1 : 1f; spaceBetweenItem = (height - flexLine.mainSize) / denominator; childBottom = height - paddingBottom; break; default: throw new IllegalStateException("Invalid justifyContent is set: " + mJustifyContent); } spaceBetweenItem = Math.max(spaceBetweenItem, 0); for (int i = 0; i < flexLine.itemCount; i++) { View child = getReorderedChildAt(currentViewIndex); if (child == null) { continue; } else if (child.getVisibility() == View.GONE) { currentViewIndex++; continue; } LayoutParams lp = ((LayoutParams) child.getLayoutParams()); childTop += lp.topMargin; childBottom -= lp.bottomMargin; if (isRtl) { if (fromBottomToTop) { layoutSingleChildVertical(child, flexLine, true, mAlignItems, childRight - child.getMeasuredWidth(), Math.round(childBottom) - child.getMeasuredHeight(), childRight, Math.round(childBottom)); } else { layoutSingleChildVertical(child, flexLine, true, mAlignItems, childRight - child.getMeasuredWidth(), Math.round(childTop), childRight, Math.round(childTop) + child.getMeasuredHeight()); } } else { if (fromBottomToTop) { layoutSingleChildVertical(child, flexLine, false, mAlignItems, childLeft, Math.round(childBottom) - child.getMeasuredHeight(), childLeft + child.getMeasuredWidth(), Math.round(childBottom)); } else { layoutSingleChildVertical(child, flexLine, false, mAlignItems, childLeft, Math.round(childTop), childLeft + child.getMeasuredWidth(), Math.round(childTop) + child.getMeasuredHeight()); } } childTop += child.getMeasuredHeight() + spaceBetweenItem + lp.bottomMargin; childBottom -= child.getMeasuredHeight() + spaceBetweenItem + lp.topMargin; currentViewIndex++; } childLeft += flexLine.crossSize; childRight -= flexLine.crossSize; } }
From source file:beichen.douban.ui.view.LazyViewPager.java
@Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { // For simple implementation, or internal size is always 0. // We depend on the container to specify the layout size of // our view. We can't really know what it is since we will be // adding and removing different arbitrary views and do not // want the layout to change as this happens. setMeasuredDimension(getDefaultSize(0, widthMeasureSpec), getDefaultSize(0, heightMeasureSpec)); // Children are just made to fill our space. int childWidthSize = getMeasuredWidth() - getPaddingLeft() - getPaddingRight(); int childHeightSize = getMeasuredHeight() - getPaddingTop() - getPaddingBottom(); /*/* w w w . j a v a 2 s . c o m*/ * Make sure all children have been properly measured. Decor views * first. Right now we cheat and make this less complicated by assuming * decor views won't intersect. We will pin to edges based on gravity. */ int size = getChildCount(); for (int i = 0; i < size; ++i) { final View child = getChildAt(i); if (child.getVisibility() != GONE) { final LayoutParams lp = (LayoutParams) child.getLayoutParams(); if (lp != null && lp.isDecor) { final int hgrav = lp.gravity & Gravity.HORIZONTAL_GRAVITY_MASK; final int vgrav = lp.gravity & Gravity.VERTICAL_GRAVITY_MASK; Log.d(TAG, "gravity: " + lp.gravity + " hgrav: " + hgrav + " vgrav: " + vgrav); int widthMode = MeasureSpec.AT_MOST; int heightMode = MeasureSpec.AT_MOST; boolean consumeVertical = vgrav == Gravity.TOP || vgrav == Gravity.BOTTOM; boolean consumeHorizontal = hgrav == Gravity.LEFT || hgrav == Gravity.RIGHT; if (consumeVertical) { widthMode = MeasureSpec.EXACTLY; } else if (consumeHorizontal) { heightMode = MeasureSpec.EXACTLY; } final int widthSpec = MeasureSpec.makeMeasureSpec(childWidthSize, widthMode); final int heightSpec = MeasureSpec.makeMeasureSpec(childHeightSize, heightMode); child.measure(widthSpec, heightSpec); if (consumeVertical) { childHeightSize -= child.getMeasuredHeight(); } else if (consumeHorizontal) { childWidthSize -= child.getMeasuredWidth(); } } } } mChildWidthMeasureSpec = MeasureSpec.makeMeasureSpec(childWidthSize, MeasureSpec.EXACTLY); mChildHeightMeasureSpec = MeasureSpec.makeMeasureSpec(childHeightSize, MeasureSpec.EXACTLY); // Make sure we have created all fragments that we need to have shown. mInLayout = true; populate(); mInLayout = false; // Page views next. size = getChildCount(); for (int i = 0; i < size; ++i) { final View child = getChildAt(i); if (child.getVisibility() != GONE) { if (DEBUG) Log.v(TAG, "Measuring #" + i + " " + child + ": " + mChildWidthMeasureSpec); final LayoutParams lp = (LayoutParams) child.getLayoutParams(); if (lp == null || !lp.isDecor) { child.measure(mChildWidthMeasureSpec, mChildHeightMeasureSpec); } } } }
From source file:beichen.douban.ui.view.LazyViewPager.java
@Override protected void onLayout(boolean changed, int l, int t, int r, int b) { mInLayout = true;//from w w w . ja va 2 s .c o m populate(); mInLayout = false; final int count = getChildCount(); int width = r - l; int height = b - t; int paddingLeft = getPaddingLeft(); int paddingTop = getPaddingTop(); int paddingRight = getPaddingRight(); int paddingBottom = getPaddingBottom(); final int scrollX = getScrollX(); int decorCount = 0; for (int i = 0; i < count; i++) { final View child = getChildAt(i); if (child.getVisibility() != GONE) { final LayoutParams lp = (LayoutParams) child.getLayoutParams(); ItemInfo ii; int childLeft = 0; int childTop = 0; if (lp.isDecor) { final int hgrav = lp.gravity & Gravity.HORIZONTAL_GRAVITY_MASK; final int vgrav = lp.gravity & Gravity.VERTICAL_GRAVITY_MASK; switch (hgrav) { default: childLeft = paddingLeft; break; case Gravity.LEFT: childLeft = paddingLeft; paddingLeft += child.getMeasuredWidth(); break; case Gravity.CENTER_HORIZONTAL: childLeft = Math.max((width - child.getMeasuredWidth()) / 2, paddingLeft); break; case Gravity.RIGHT: childLeft = width - paddingRight - child.getMeasuredWidth(); paddingRight += child.getMeasuredWidth(); break; } switch (vgrav) { default: childTop = paddingTop; break; case Gravity.TOP: childTop = paddingTop; paddingTop += child.getMeasuredHeight(); break; case Gravity.CENTER_VERTICAL: childTop = Math.max((height - child.getMeasuredHeight()) / 2, paddingTop); break; case Gravity.BOTTOM: childTop = height - paddingBottom - child.getMeasuredHeight(); paddingBottom += child.getMeasuredHeight(); break; } childLeft += scrollX; decorCount++; child.layout(childLeft, childTop, childLeft + child.getMeasuredWidth(), childTop + child.getMeasuredHeight()); } else if ((ii = infoForChild(child)) != null) { int loff = (width + mPageMargin) * ii.position; childLeft = paddingLeft + loff; childTop = paddingTop; if (DEBUG) Log.v(TAG, "Positioning #" + i + " " + child + " f=" + ii.object + ":" + childLeft + "," + childTop + " " + child.getMeasuredWidth() + "x" + child.getMeasuredHeight()); child.layout(childLeft, childTop, childLeft + child.getMeasuredWidth(), childTop + child.getMeasuredHeight()); } } } mTopPageBounds = paddingTop; mBottomPageBounds = height - paddingBottom; mDecorChildCount = decorCount; mFirstLayout = false; }
From source file:android.support.v7.widget.LinearLayoutCompat.java
/** * Measures the children when the orientation of this LinearLayout is set * to {@link #HORIZONTAL}./*w w w . j av a 2 s.c o m*/ * * @param widthMeasureSpec Horizontal space requirements as imposed by the parent. * @param heightMeasureSpec Vertical space requirements as imposed by the parent. * * @see #getOrientation() * @see #setOrientation(int) * @see #onMeasure(int, int) */ void measureHorizontal(int widthMeasureSpec, int heightMeasureSpec) { mTotalLength = 0; int maxHeight = 0; int childState = 0; int alternativeMaxHeight = 0; int weightedMaxHeight = 0; boolean allFillParent = true; float totalWeight = 0; final int count = getVirtualChildCount(); final int widthMode = MeasureSpec.getMode(widthMeasureSpec); final int heightMode = MeasureSpec.getMode(heightMeasureSpec); boolean matchHeight = false; boolean skippedMeasure = false; if (mMaxAscent == null || mMaxDescent == null) { mMaxAscent = new int[VERTICAL_GRAVITY_COUNT]; mMaxDescent = new int[VERTICAL_GRAVITY_COUNT]; } final int[] maxAscent = mMaxAscent; final int[] maxDescent = mMaxDescent; maxAscent[0] = maxAscent[1] = maxAscent[2] = maxAscent[3] = -1; maxDescent[0] = maxDescent[1] = maxDescent[2] = maxDescent[3] = -1; final boolean baselineAligned = mBaselineAligned; final boolean useLargestChild = mUseLargestChild; final boolean isExactly = widthMode == MeasureSpec.EXACTLY; int largestChildWidth = Integer.MIN_VALUE; // See how wide everyone is. Also remember max height. for (int i = 0; i < count; ++i) { final View child = getVirtualChildAt(i); if (child == null) { mTotalLength += measureNullChild(i); continue; } if (child.getVisibility() == GONE) { i += getChildrenSkipCount(child, i); continue; } if (hasDividerBeforeChildAt(i)) { mTotalLength += mDividerWidth; } final LinearLayoutCompat.LayoutParams lp = (LinearLayoutCompat.LayoutParams) child.getLayoutParams(); totalWeight += lp.weight; if (widthMode == MeasureSpec.EXACTLY && lp.width == 0 && lp.weight > 0) { // Optimization: don't bother measuring children who are going to use // leftover space. These views will get measured again down below if // there is any leftover space. if (isExactly) { mTotalLength += lp.leftMargin + lp.rightMargin; } else { final int totalLength = mTotalLength; mTotalLength = Math.max(totalLength, totalLength + lp.leftMargin + lp.rightMargin); } // Baseline alignment requires to measure widgets to obtain the // baseline offset (in particular for TextViews). The following // defeats the optimization mentioned above. Allow the child to // use as much space as it wants because we can shrink things // later (and re-measure). if (baselineAligned) { final int freeSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED); child.measure(freeSpec, freeSpec); } else { skippedMeasure = true; } } else { int oldWidth = Integer.MIN_VALUE; if (lp.width == 0 && lp.weight > 0) { // widthMode is either UNSPECIFIED or AT_MOST, and this // child // wanted to stretch to fill available space. Translate that to // WRAP_CONTENT so that it does not end up with a width of 0 oldWidth = 0; lp.width = LayoutParams.WRAP_CONTENT; } // Determine how big this child would like to be. If this or // previous children have given a weight, then we allow it to // use all available space (and we will shrink things later // if needed). measureChildBeforeLayout(child, i, widthMeasureSpec, totalWeight == 0 ? mTotalLength : 0, heightMeasureSpec, 0); if (oldWidth != Integer.MIN_VALUE) { lp.width = oldWidth; } final int childWidth = child.getMeasuredWidth(); if (isExactly) { mTotalLength += childWidth + lp.leftMargin + lp.rightMargin + getNextLocationOffset(child); } else { final int totalLength = mTotalLength; mTotalLength = Math.max(totalLength, totalLength + childWidth + lp.leftMargin + lp.rightMargin + getNextLocationOffset(child)); } if (useLargestChild) { largestChildWidth = Math.max(childWidth, largestChildWidth); } } boolean matchHeightLocally = false; if (heightMode != MeasureSpec.EXACTLY && lp.height == LayoutParams.MATCH_PARENT) { // The height of the linear layout will scale, and at least one // child said it wanted to match our height. Set a flag indicating that // we need to remeasure at least that view when we know our height. matchHeight = true; matchHeightLocally = true; } final int margin = lp.topMargin + lp.bottomMargin; final int childHeight = child.getMeasuredHeight() + margin; childState = ViewUtils.combineMeasuredStates(childState, ViewCompat.getMeasuredState(child)); if (baselineAligned) { final int childBaseline = child.getBaseline(); if (childBaseline != -1) { // Translates the child's vertical gravity into an index // in the range 0..VERTICAL_GRAVITY_COUNT final int gravity = (lp.gravity < 0 ? mGravity : lp.gravity) & Gravity.VERTICAL_GRAVITY_MASK; final int index = ((gravity >> Gravity.AXIS_Y_SHIFT) & ~Gravity.AXIS_SPECIFIED) >> 1; maxAscent[index] = Math.max(maxAscent[index], childBaseline); maxDescent[index] = Math.max(maxDescent[index], childHeight - childBaseline); } } maxHeight = Math.max(maxHeight, childHeight); allFillParent = allFillParent && lp.height == LayoutParams.MATCH_PARENT; if (lp.weight > 0) { /* * Heights of weighted Views are bogus if we end up * remeasuring, so keep them separate. */ weightedMaxHeight = Math.max(weightedMaxHeight, matchHeightLocally ? margin : childHeight); } else { alternativeMaxHeight = Math.max(alternativeMaxHeight, matchHeightLocally ? margin : childHeight); } i += getChildrenSkipCount(child, i); } if (mTotalLength > 0 && hasDividerBeforeChildAt(count)) { mTotalLength += mDividerWidth; } // Check mMaxAscent[INDEX_TOP] first because it maps to Gravity.TOP, // the most common case if (maxAscent[INDEX_TOP] != -1 || maxAscent[INDEX_CENTER_VERTICAL] != -1 || maxAscent[INDEX_BOTTOM] != -1 || maxAscent[INDEX_FILL] != -1) { final int ascent = Math.max(maxAscent[INDEX_FILL], Math.max(maxAscent[INDEX_CENTER_VERTICAL], Math.max(maxAscent[INDEX_TOP], maxAscent[INDEX_BOTTOM]))); final int descent = Math.max(maxDescent[INDEX_FILL], Math.max(maxDescent[INDEX_CENTER_VERTICAL], Math.max(maxDescent[INDEX_TOP], maxDescent[INDEX_BOTTOM]))); maxHeight = Math.max(maxHeight, ascent + descent); } if (useLargestChild && (widthMode == MeasureSpec.AT_MOST || widthMode == MeasureSpec.UNSPECIFIED)) { mTotalLength = 0; for (int i = 0; i < count; ++i) { final View child = getVirtualChildAt(i); if (child == null) { mTotalLength += measureNullChild(i); continue; } if (child.getVisibility() == GONE) { i += getChildrenSkipCount(child, i); continue; } final LinearLayoutCompat.LayoutParams lp = (LinearLayoutCompat.LayoutParams) child .getLayoutParams(); if (isExactly) { mTotalLength += largestChildWidth + lp.leftMargin + lp.rightMargin + getNextLocationOffset(child); } else { final int totalLength = mTotalLength; mTotalLength = Math.max(totalLength, totalLength + largestChildWidth + lp.leftMargin + lp.rightMargin + getNextLocationOffset(child)); } } } // Add in our padding mTotalLength += getPaddingLeft() + getPaddingRight(); int widthSize = mTotalLength; // Check against our minimum width widthSize = Math.max(widthSize, getSuggestedMinimumWidth()); // Reconcile our calculated size with the widthMeasureSpec int widthSizeAndState = ViewCompat.resolveSizeAndState(widthSize, widthMeasureSpec, 0); widthSize = widthSizeAndState & ViewCompat.MEASURED_SIZE_MASK; // Either expand children with weight to take up available space or // shrink them if they extend beyond our current bounds. If we skipped // measurement on any children, we need to measure them now. int delta = widthSize - mTotalLength; if (skippedMeasure || delta != 0 && totalWeight > 0.0f) { float weightSum = mWeightSum > 0.0f ? mWeightSum : totalWeight; maxAscent[0] = maxAscent[1] = maxAscent[2] = maxAscent[3] = -1; maxDescent[0] = maxDescent[1] = maxDescent[2] = maxDescent[3] = -1; maxHeight = -1; mTotalLength = 0; for (int i = 0; i < count; ++i) { final View child = getVirtualChildAt(i); if (child == null || child.getVisibility() == View.GONE) { continue; } final LinearLayoutCompat.LayoutParams lp = (LinearLayoutCompat.LayoutParams) child .getLayoutParams(); float childExtra = lp.weight; if (childExtra > 0) { // Child said it could absorb extra space -- give him his share int share = (int) (childExtra * delta / weightSum); weightSum -= childExtra; delta -= share; final int childHeightMeasureSpec = getChildMeasureSpec(heightMeasureSpec, getPaddingTop() + getPaddingBottom() + lp.topMargin + lp.bottomMargin, lp.height); // TODO: Use a field like lp.isMeasured to figure out if this // child has been previously measured if ((lp.width != 0) || (widthMode != MeasureSpec.EXACTLY)) { // child was measured once already above ... base new measurement // on stored values int childWidth = child.getMeasuredWidth() + share; if (childWidth < 0) { childWidth = 0; } child.measure(MeasureSpec.makeMeasureSpec(childWidth, MeasureSpec.EXACTLY), childHeightMeasureSpec); } else { // child was skipped in the loop above. Measure for this first time here child.measure(MeasureSpec.makeMeasureSpec(share > 0 ? share : 0, MeasureSpec.EXACTLY), childHeightMeasureSpec); } // Child may now not fit in horizontal dimension. childState = ViewUtils.combineMeasuredStates(childState, ViewCompat.getMeasuredState(child) & ViewCompat.MEASURED_STATE_MASK); } if (isExactly) { mTotalLength += child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin + getNextLocationOffset(child); } else { final int totalLength = mTotalLength; mTotalLength = Math.max(totalLength, totalLength + child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin + getNextLocationOffset(child)); } boolean matchHeightLocally = heightMode != MeasureSpec.EXACTLY && lp.height == LayoutParams.MATCH_PARENT; final int margin = lp.topMargin + lp.bottomMargin; int childHeight = child.getMeasuredHeight() + margin; maxHeight = Math.max(maxHeight, childHeight); alternativeMaxHeight = Math.max(alternativeMaxHeight, matchHeightLocally ? margin : childHeight); allFillParent = allFillParent && lp.height == LayoutParams.MATCH_PARENT; if (baselineAligned) { final int childBaseline = child.getBaseline(); if (childBaseline != -1) { // Translates the child's vertical gravity into an index in the range 0..2 final int gravity = (lp.gravity < 0 ? mGravity : lp.gravity) & Gravity.VERTICAL_GRAVITY_MASK; final int index = ((gravity >> Gravity.AXIS_Y_SHIFT) & ~Gravity.AXIS_SPECIFIED) >> 1; maxAscent[index] = Math.max(maxAscent[index], childBaseline); maxDescent[index] = Math.max(maxDescent[index], childHeight - childBaseline); } } } // Add in our padding mTotalLength += getPaddingLeft() + getPaddingRight(); // TODO: Should we update widthSize with the new total length? // Check mMaxAscent[INDEX_TOP] first because it maps to Gravity.TOP, // the most common case if (maxAscent[INDEX_TOP] != -1 || maxAscent[INDEX_CENTER_VERTICAL] != -1 || maxAscent[INDEX_BOTTOM] != -1 || maxAscent[INDEX_FILL] != -1) { final int ascent = Math.max(maxAscent[INDEX_FILL], Math.max(maxAscent[INDEX_CENTER_VERTICAL], Math.max(maxAscent[INDEX_TOP], maxAscent[INDEX_BOTTOM]))); final int descent = Math.max(maxDescent[INDEX_FILL], Math.max(maxDescent[INDEX_CENTER_VERTICAL], Math.max(maxDescent[INDEX_TOP], maxDescent[INDEX_BOTTOM]))); maxHeight = Math.max(maxHeight, ascent + descent); } } else { alternativeMaxHeight = Math.max(alternativeMaxHeight, weightedMaxHeight); // We have no limit, so make all weighted views as wide as the largest child. // Children will have already been measured once. if (useLargestChild && widthMode != MeasureSpec.EXACTLY) { for (int i = 0; i < count; i++) { final View child = getVirtualChildAt(i); if (child == null || child.getVisibility() == View.GONE) { continue; } final LinearLayoutCompat.LayoutParams lp = (LinearLayoutCompat.LayoutParams) child .getLayoutParams(); float childExtra = lp.weight; if (childExtra > 0) { child.measure(MeasureSpec.makeMeasureSpec(largestChildWidth, MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(child.getMeasuredHeight(), MeasureSpec.EXACTLY)); } } } } if (!allFillParent && heightMode != MeasureSpec.EXACTLY) { maxHeight = alternativeMaxHeight; } maxHeight += getPaddingTop() + getPaddingBottom(); // Check against our minimum height maxHeight = Math.max(maxHeight, getSuggestedMinimumHeight()); setMeasuredDimension(widthSizeAndState | (childState & ViewCompat.MEASURED_STATE_MASK), ViewCompat.resolveSizeAndState(maxHeight, heightMeasureSpec, (childState << ViewCompat.MEASURED_HEIGHT_STATE_SHIFT))); if (matchHeight) { forceUniformHeight(count, widthMeasureSpec); } }
From source file:com.devabit.takestock.ui.widget.FlexboxLayout.java
/** * Sub method for {@link #onMeasure(int, int)} when the main axis direction is vertical * (either from top to bottom or bottom to top). * * @param widthMeasureSpec horizontal space requirements as imposed by the parent * @param heightMeasureSpec vertical space requirements as imposed by the parent * @see #onMeasure(int, int)/* w w w. ja va 2 s . c om*/ * @see #setFlexDirection(int) * @see #setFlexWrap(int) * @see #setAlignItems(int) * @see #setAlignContent(int) */ private void measureVertical(int widthMeasureSpec, int heightMeasureSpec) { int heightMode = MeasureSpec.getMode(heightMeasureSpec); int heightSize = MeasureSpec.getSize(heightMeasureSpec); int childState = 0; mFlexLines.clear(); // Determine how many flex lines are needed in this layout by measuring each child. // (Expand or shrink the view depending on the flexGrow and flexShrink attributes in a later // loop) int childCount = getChildCount(); int paddingTop = getPaddingTop(); int paddingBottom = getPaddingBottom(); int largestWidthInColumn = Integer.MIN_VALUE; FlexLine flexLine = new FlexLine(); flexLine.mainSize = paddingTop + paddingBottom; for (int i = 0; i < childCount; i++) { View child = getReorderedChildAt(i); if (child == null) { addFlexLineIfLastFlexItem(i, childCount, flexLine); continue; } else if (child.getVisibility() == View.GONE) { flexLine.itemCount++; addFlexLineIfLastFlexItem(i, childCount, flexLine); continue; } FlexboxLayout.LayoutParams lp = (LayoutParams) child.getLayoutParams(); if (lp.alignSelf == LayoutParams.ALIGN_SELF_STRETCH) { flexLine.indicesAlignSelfStretch.add(i); } int childHeight = lp.height; if (lp.flexBasisPercent != LayoutParams.FLEX_BASIS_PERCENT_DEFAULT && heightMode == MeasureSpec.EXACTLY) { childHeight = Math.round(heightSize * lp.flexBasisPercent); // Use the dimension from the layout_height attribute if the heightMode is not // MeasureSpec.EXACTLY even if any fraction value is set to layout_flexBasisPercent. // There are likely quite few use cases where assigning any fraction values // with heightMode is not MeasureSpec.EXACTLY (e.g. FlexboxLayout's layout_height // is set to wrap_content) } int childWidthMeasureSpec = getChildMeasureSpec(widthMeasureSpec, getPaddingLeft() + getPaddingRight() + lp.leftMargin + lp.rightMargin, lp.width); int childHeightMeasureSpec = getChildMeasureSpec(heightMeasureSpec, getPaddingTop() + getPaddingBottom() + lp.topMargin + lp.bottomMargin, childHeight); child.measure(childWidthMeasureSpec, childHeightMeasureSpec); // Check the size constraint after the first measurement for the child // To prevent the child's width/height violate the size constraints imposed by the // {@link LayoutParams#minWidth}, {@link LayoutParams#minHeight}, // {@link LayoutParams#maxWidth} and {@link LayoutParams#maxHeight} attributes. // E.g. When the child's layout_height is wrap_content the measured height may be // less than the min height after the first measurement. checkSizeConstraints(child); childState = ViewCompat.combineMeasuredStates(childState, ViewCompat.getMeasuredState(child)); largestWidthInColumn = Math.max(largestWidthInColumn, child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin); if (isWrapRequired(mFlexWrap, heightMode, heightSize, flexLine.mainSize, child.getMeasuredHeight() + lp.topMargin + lp.bottomMargin, lp)) { if (flexLine.itemCount > 0) { mFlexLines.add(flexLine); } flexLine = new FlexLine(); flexLine.itemCount = 1; flexLine.mainSize = paddingTop + paddingBottom; largestWidthInColumn = child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin; } else { flexLine.itemCount++; } flexLine.mainSize += child.getMeasuredHeight() + lp.topMargin + lp.bottomMargin; flexLine.totalFlexGrow += lp.flexGrow; flexLine.totalFlexShrink += lp.flexShrink; // Temporarily set the cross axis length as the largest child width in the column // Expand along the cross axis depending on the mAlignContent property if needed // later flexLine.crossSize = Math.max(flexLine.crossSize, largestWidthInColumn); addFlexLineIfLastFlexItem(i, childCount, flexLine); } determineMainSize(mFlexDirection, widthMeasureSpec, heightMeasureSpec); determineCrossSize(mFlexDirection, widthMeasureSpec, heightMeasureSpec, getPaddingLeft() + getPaddingRight()); // Now cross size for each flex line is determined. // Expand the views if alignItems (or alignSelf in each child view) is set to stretch stretchViews(mFlexDirection, mAlignItems); setMeasuredDimensionForFlex(mFlexDirection, widthMeasureSpec, heightMeasureSpec, childState); }
From source file:com.devabit.takestock.ui.widget.FlexboxLayout.java
/** * Sub method for {@link #onMeasure(int, int)}, when the main axis direction is horizontal * (either left to right or right to left). * * @param widthMeasureSpec horizontal space requirements as imposed by the parent * @param heightMeasureSpec vertical space requirements as imposed by the parent * @see #onMeasure(int, int)/*from w ww . j a v a2s. c o m*/ * @see #setFlexDirection(int) * @see #setFlexWrap(int) * @see #setAlignItems(int) * @see #setAlignContent(int) */ private void measureHorizontal(int widthMeasureSpec, int heightMeasureSpec) { int widthMode = MeasureSpec.getMode(widthMeasureSpec); int widthSize = MeasureSpec.getSize(widthMeasureSpec); int childState = 0; mFlexLines.clear(); // Determine how many flex lines are needed in this layout by measuring each child. // (Expand or shrink the view depending on the flexGrow and flexShrink attributes in a later // loop) { int childCount = getChildCount(); int paddingStart = ViewCompat.getPaddingStart(this); int paddingEnd = ViewCompat.getPaddingEnd(this); int largestHeightInRow = Integer.MIN_VALUE; FlexLine flexLine = new FlexLine(); flexLine.mainSize = paddingStart + paddingEnd; for (int i = 0; i < childCount; i++) { View child = getReorderedChildAt(i); if (child == null) { addFlexLineIfLastFlexItem(i, childCount, flexLine); continue; } else if (child.getVisibility() == View.GONE) { flexLine.itemCount++; addFlexLineIfLastFlexItem(i, childCount, flexLine); continue; } FlexboxLayout.LayoutParams lp = (LayoutParams) child.getLayoutParams(); if (lp.alignSelf == LayoutParams.ALIGN_SELF_STRETCH) { flexLine.indicesAlignSelfStretch.add(i); } int childWidth = lp.width; if (lp.flexBasisPercent != LayoutParams.FLEX_BASIS_PERCENT_DEFAULT && widthMode == MeasureSpec.EXACTLY) { childWidth = Math.round(widthSize * lp.flexBasisPercent); // Use the dimension from the layout_width attribute if the widthMode is not // MeasureSpec.EXACTLY even if any fraction value is set to // layout_flexBasisPercent. // There are likely quite few use cases where assigning any fraction values // with widthMode is not MeasureSpec.EXACTLY (e.g. FlexboxLayout's layout_width // is set to wrap_content) } int childWidthMeasureSpec = getChildMeasureSpec(widthMeasureSpec, getPaddingLeft() + getPaddingRight() + lp.leftMargin + lp.rightMargin, childWidth); int childHeightMeasureSpec = getChildMeasureSpec(heightMeasureSpec, getPaddingTop() + getPaddingBottom() + lp.topMargin + lp.bottomMargin, lp.height); child.measure(childWidthMeasureSpec, childHeightMeasureSpec); // Check the size constraint after the first measurement for the child // To prevent the child's width/height violate the size constraints imposed by the // {@link LayoutParams#minWidth}, {@link LayoutParams#minHeight}, // {@link LayoutParams#maxWidth} and {@link LayoutParams#maxHeight} attributes. // E.g. When the child's layout_width is wrap_content the measured width may be // less than the min width after the first measurement. checkSizeConstraints(child); childState = ViewCompat.combineMeasuredStates(childState, ViewCompat.getMeasuredState(child)); largestHeightInRow = Math.max(largestHeightInRow, child.getMeasuredHeight() + lp.topMargin + lp.bottomMargin); if (isWrapRequired(mFlexWrap, widthMode, widthSize, flexLine.mainSize, child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin, lp)) { if (flexLine.itemCount > 0) { mFlexLines.add(flexLine); } flexLine = new FlexLine(); flexLine.itemCount = 1; flexLine.mainSize = paddingStart + paddingEnd; largestHeightInRow = child.getMeasuredHeight() + lp.topMargin + lp.bottomMargin; } else { flexLine.itemCount++; } flexLine.mainSize += child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin; flexLine.totalFlexGrow += lp.flexGrow; flexLine.totalFlexShrink += lp.flexShrink; // Temporarily set the cross axis length as the largest child in the row // Expand along the cross axis depending on the mAlignContent property if needed // later flexLine.crossSize = Math.max(flexLine.crossSize, largestHeightInRow); if (mFlexWrap != FLEX_WRAP_WRAP_REVERSE) { flexLine.maxBaseline = Math.max(flexLine.maxBaseline, child.getBaseline() + lp.topMargin); } else { // if the flex wrap property is FLEX_WRAP_WRAP_REVERSE, calculate the // baseline as the distance from the cross end and the baseline // since the cross size calculation is based on the distance from the cross end flexLine.maxBaseline = Math.max(flexLine.maxBaseline, child.getMeasuredHeight() - child.getBaseline() + lp.bottomMargin); } addFlexLineIfLastFlexItem(i, childCount, flexLine); } } determineMainSize(mFlexDirection, widthMeasureSpec, heightMeasureSpec); // TODO: Consider the case any individual child's alignSelf is set to ALIGN_SELF_BASELINE if (mAlignItems == ALIGN_ITEMS_BASELINE) { int viewIndex = 0; for (FlexLine flexLine : mFlexLines) { // The largest height value that also take the baseline shift into account int largestHeightInLine = Integer.MIN_VALUE; for (int i = viewIndex; i < viewIndex + flexLine.itemCount; i++) { View child = getReorderedChildAt(i); LayoutParams lp = (LayoutParams) child.getLayoutParams(); if (mFlexWrap != FLEX_WRAP_WRAP_REVERSE) { int marginTop = flexLine.maxBaseline - child.getBaseline(); marginTop = Math.max(marginTop, lp.topMargin); largestHeightInLine = Math.max(largestHeightInLine, child.getHeight() + marginTop + lp.bottomMargin); } else { int marginBottom = flexLine.maxBaseline - child.getMeasuredHeight() + child.getBaseline(); marginBottom = Math.max(marginBottom, lp.bottomMargin); largestHeightInLine = Math.max(largestHeightInLine, child.getHeight() + lp.topMargin + marginBottom); } } flexLine.crossSize = largestHeightInLine; viewIndex += flexLine.itemCount; } } determineCrossSize(mFlexDirection, widthMeasureSpec, heightMeasureSpec, getPaddingTop() + getPaddingBottom()); // Now cross size for each flex line is determined. // Expand the views if alignItems (or alignSelf in each child view) is set to stretch stretchViews(mFlexDirection, mAlignItems); setMeasuredDimensionForFlex(mFlexDirection, widthMeasureSpec, heightMeasureSpec, childState); }
From source file:administrator.example.com.myscrollview.VerticalViewPager.java
/** * We only want the current page that is being shown to be touchable. *///from www .jav a 2s . com @Override public void addTouchables(ArrayList<View> views) { // Note that we don't call super.addTouchables(), which means that // we don't call View.addTouchables(). This is okay because a ViewPager // is itself not touchable. for (int i = 0; i < getChildCount(); i++) { final View child = getChildAt(i); if (child.getVisibility() == VISIBLE) { ItemInfo ii = infoForChild(child); if (ii != null && ii.position == mCurItem) { child.addTouchables(views); } /* end of if */ } /* end of if */ } /* end of for */ }