List of usage examples for android.view View combineMeasuredStates
public static int combineMeasuredStates(int curState, int newState)
From source file:com.google.android.flexbox.FlexboxHelper.java
/** * Calculates how many flex lines are needed in the flex container layout by measuring each * child.// w w w . j av a2s. co m * Expanding or shrinking the flex items depending on the flex grow and flex shrink * attributes are done in a later procedure, so the views' measured width and measured * height may be changed in a later process. * * @param result an instance of {@link FlexLinesResult} that is going to contain a * list of flex lines and the child state used by * {@link View#setMeasuredDimension(int, int)}. * @param mainMeasureSpec the main axis measure spec imposed by the flex container, * width for horizontal direction, height otherwise * @param crossMeasureSpec the cross axis measure spec imposed by the flex container, * height for horizontal direction, width otherwise * @param needsCalcAmount the amount of pixels where flex line calculation should be stopped * this is needed to avoid the expensive calculation if the * calculation is needed only the small part of the entire flex * container. (E.g. If the flex container is the * {@link FlexboxLayoutManager}, the calculation only needs the * visible area, imposing the entire calculation may cause bad * performance * @param fromIndex the index of the child from which the calculation starts * @param toIndex the index of the child to which the calculation ends (until the * flex line which include the which who has that index). If this * and needsCalcAmount are both set, first flex lines are calculated * to the index, calculate the amount of pixels as the needsCalcAmount * argument in addition to that * @param existingLines If not null, calculated flex lines will be added to this instance */ void calculateFlexLines(FlexLinesResult result, int mainMeasureSpec, int crossMeasureSpec, int needsCalcAmount, int fromIndex, int toIndex, @Nullable List<FlexLine> existingLines) { boolean isMainHorizontal = mFlexContainer.isMainAxisDirectionHorizontal(); int mainMode = View.MeasureSpec.getMode(mainMeasureSpec); int mainSize = View.MeasureSpec.getSize(mainMeasureSpec); int childState = 0; List<FlexLine> flexLines; if (existingLines == null) { flexLines = new ArrayList<>(); } else { flexLines = existingLines; } result.mFlexLines = flexLines; boolean reachedToIndex = toIndex == NO_POSITION; int mainPaddingStart = getPaddingStartMain(isMainHorizontal); int mainPaddingEnd = getPaddingEndMain(isMainHorizontal); int crossPaddingStart = getPaddingStartCross(isMainHorizontal); int crossPaddingEnd = getPaddingEndCross(isMainHorizontal); int largestSizeInCross = Integer.MIN_VALUE; // The amount of cross size calculated in this method call. int sumCrossSize = 0; // The index of the view in the flex line. int indexInFlexLine = 0; FlexLine flexLine = new FlexLine(); flexLine.mFirstIndex = fromIndex; flexLine.mMainSize = mainPaddingStart + mainPaddingEnd; int childCount = mFlexContainer.getFlexItemCount(); for (int i = fromIndex; i < childCount; i++) { View child = mFlexContainer.getReorderedFlexItemAt(i); if (child == null) { if (isLastFlexItem(i, childCount, flexLine)) { addFlexLine(flexLines, flexLine, i, sumCrossSize); } continue; } else if (child.getVisibility() == View.GONE) { flexLine.mGoneItemCount++; flexLine.mItemCount++; if (isLastFlexItem(i, childCount, flexLine)) { addFlexLine(flexLines, flexLine, i, sumCrossSize); } continue; } FlexItem flexItem = (FlexItem) child.getLayoutParams(); if (flexItem.getAlignSelf() == AlignItems.STRETCH) { flexLine.mIndicesAlignSelfStretch.add(i); } int childMainSize = getFlexItemSizeMain(flexItem, isMainHorizontal); if (flexItem.getFlexBasisPercent() != FLEX_BASIS_PERCENT_DEFAULT && mainMode == View.MeasureSpec.EXACTLY) { childMainSize = Math.round(mainSize * flexItem.getFlexBasisPercent()); // Use the dimension from the layout if the mainMode is not // MeasureSpec.EXACTLY even if any fraction value is set to // layout_flexBasisPercent. } int childMainMeasureSpec; int childCrossMeasureSpec; if (isMainHorizontal) { childMainMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(mainMeasureSpec, mainPaddingStart + mainPaddingEnd + getFlexItemMarginStartMain(flexItem, true) + getFlexItemMarginEndMain(flexItem, true), childMainSize); childCrossMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(crossMeasureSpec, crossPaddingStart + crossPaddingEnd + getFlexItemMarginStartCross(flexItem, true) + getFlexItemMarginEndCross(flexItem, true) + sumCrossSize, getFlexItemSizeCross(flexItem, true)); child.measure(childMainMeasureSpec, childCrossMeasureSpec); updateMeasureCache(i, childMainMeasureSpec, childCrossMeasureSpec, child); } else { childCrossMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(crossMeasureSpec, crossPaddingStart + crossPaddingEnd + getFlexItemMarginStartCross(flexItem, false) + getFlexItemMarginEndCross(flexItem, false) + sumCrossSize, getFlexItemSizeCross(flexItem, false)); childMainMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(mainMeasureSpec, mainPaddingStart + mainPaddingEnd + getFlexItemMarginStartMain(flexItem, false) + getFlexItemMarginEndMain(flexItem, false), childMainSize); child.measure(childCrossMeasureSpec, childMainMeasureSpec); updateMeasureCache(i, childCrossMeasureSpec, childMainMeasureSpec, child); } mFlexContainer.updateViewCache(i, child); // 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 FlexItem#getMinWidth()}, {@link FlexItem#getMinHeight()}, // {@link FlexItem#getMaxWidth()} and {@link FlexItem#getMaxHeight()} 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, i); childState = View.combineMeasuredStates(childState, child.getMeasuredState()); if (isWrapRequired(child, mainMode, mainSize, flexLine.mMainSize, getViewMeasuredSizeMain(child, isMainHorizontal) + getFlexItemMarginStartMain(flexItem, isMainHorizontal) + getFlexItemMarginEndMain(flexItem, isMainHorizontal), flexItem, i, indexInFlexLine, flexLines.size())) { if (flexLine.getItemCountNotGone() > 0) { addFlexLine(flexLines, flexLine, i > 0 ? i - 1 : 0, sumCrossSize); sumCrossSize += flexLine.mCrossSize; } if (isMainHorizontal) { if (flexItem.getHeight() == ViewGroup.LayoutParams.MATCH_PARENT) { // This case takes care of the corner case where the cross size of the // child is affected by the just added flex line. // E.g. when the child's layout_height is set to match_parent, the height // of that child needs to be determined taking the total cross size used // so far into account. In that case, the height of the child needs to be // measured again note that we don't need to judge if the wrapping occurs // because it doesn't change the size along the main axis. childCrossMeasureSpec = mFlexContainer.getChildHeightMeasureSpec(crossMeasureSpec, mFlexContainer.getPaddingTop() + mFlexContainer.getPaddingBottom() + flexItem.getMarginTop() + flexItem.getMarginBottom() + sumCrossSize, flexItem.getHeight()); child.measure(childMainMeasureSpec, childCrossMeasureSpec); checkSizeConstraints(child, i); } } else { if (flexItem.getWidth() == ViewGroup.LayoutParams.MATCH_PARENT) { // This case takes care of the corner case where the cross size of the // child is affected by the just added flex line. // E.g. when the child's layout_width is set to match_parent, the width // of that child needs to be determined taking the total cross size used // so far into account. In that case, the width of the child needs to be // measured again note that we don't need to judge if the wrapping occurs // because it doesn't change the size along the main axis. childCrossMeasureSpec = mFlexContainer.getChildWidthMeasureSpec(crossMeasureSpec, mFlexContainer.getPaddingLeft() + mFlexContainer.getPaddingRight() + flexItem.getMarginLeft() + flexItem.getMarginRight() + sumCrossSize, flexItem.getWidth()); child.measure(childCrossMeasureSpec, childMainMeasureSpec); checkSizeConstraints(child, i); } } flexLine = new FlexLine(); flexLine.mItemCount = 1; flexLine.mMainSize = mainPaddingStart + mainPaddingEnd; flexLine.mFirstIndex = i; indexInFlexLine = 0; largestSizeInCross = Integer.MIN_VALUE; } else { flexLine.mItemCount++; indexInFlexLine++; } if (mIndexToFlexLine != null) { mIndexToFlexLine[i] = flexLines.size(); } flexLine.mMainSize += getViewMeasuredSizeMain(child, isMainHorizontal) + getFlexItemMarginStartMain(flexItem, isMainHorizontal) + getFlexItemMarginEndMain(flexItem, isMainHorizontal); flexLine.mTotalFlexGrow += flexItem.getFlexGrow(); flexLine.mTotalFlexShrink += flexItem.getFlexShrink(); mFlexContainer.onNewFlexItemAdded(child, i, indexInFlexLine, flexLine); largestSizeInCross = Math.max(largestSizeInCross, getViewMeasuredSizeCross(child, isMainHorizontal) + getFlexItemMarginStartCross(flexItem, isMainHorizontal) + getFlexItemMarginEndCross(flexItem, isMainHorizontal) + mFlexContainer.getDecorationLengthCrossAxis(child)); // Temporarily set the cross axis length as the largest child in the flexLine // Expand along the cross axis depending on the mAlignContent property if needed // later flexLine.mCrossSize = Math.max(flexLine.mCrossSize, largestSizeInCross); if (isMainHorizontal) { if (mFlexContainer.getFlexWrap() != FlexWrap.WRAP_REVERSE) { flexLine.mMaxBaseline = Math.max(flexLine.mMaxBaseline, child.getBaseline() + flexItem.getMarginTop()); } else { // if the flex wrap property is 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.mMaxBaseline = Math.max(flexLine.mMaxBaseline, child.getMeasuredHeight() - child.getBaseline() + flexItem.getMarginBottom()); } } if (isLastFlexItem(i, childCount, flexLine)) { addFlexLine(flexLines, flexLine, i, sumCrossSize); sumCrossSize += flexLine.mCrossSize; } if (toIndex != NO_POSITION && flexLines.size() > 0 && flexLines.get(flexLines.size() - 1).mLastIndex >= toIndex && i >= toIndex && !reachedToIndex) { // Calculated to include a flex line which includes the flex item having the // toIndex. // Let the sumCrossSize start from the negative value of the last flex line's // cross size because otherwise flex lines aren't calculated enough to fill the // visible area. sumCrossSize = -flexLine.getCrossSize(); reachedToIndex = true; } if (sumCrossSize > needsCalcAmount && reachedToIndex) { // Stop the calculation if the sum of cross size calculated reached to the point // beyond the needsCalcAmount value to avoid unneeded calculation in a // RecyclerView. // To be precise, the decoration length may be added to the sumCrossSize, // but we omit adding the decoration length because even without the decorator // length, it's guaranteed that calculation is done at least beyond the // needsCalcAmount break; } } result.mChildState = childState; }
From source file:vapor.view.VaporView.java
/** * Merge two states as returned by measuredState(). * //from w w w . ja v a 2 s . c om * @param currentState * The current state as returned from a view or the result of * combining multiple views. * @param newState * The new view state to combine. * @return Returns a new integer reflecting the combination of the two * states. */ public static int combine(int currentState, int newState) { return View.combineMeasuredStates(currentState, newState); }