diff options
Diffstat (limited to 'core/java/android/widget/GridLayout.java')
| -rw-r--r-- | core/java/android/widget/GridLayout.java | 187 |
1 files changed, 121 insertions, 66 deletions
diff --git a/core/java/android/widget/GridLayout.java b/core/java/android/widget/GridLayout.java index 230900176a68..54cc3f498b4d 100644 --- a/core/java/android/widget/GridLayout.java +++ b/core/java/android/widget/GridLayout.java @@ -24,7 +24,9 @@ import android.graphics.Insets; import android.graphics.Paint; import android.util.AttributeSet; import android.util.Log; +import android.util.LogPrinter; import android.util.Pair; +import android.util.Printer; import android.view.Gravity; import android.view.View; import android.view.ViewGroup; @@ -124,6 +126,17 @@ import static java.lang.Math.min; * GridLayout's algorithms favour rows and columns that are closer to its <em>right</em> * and <em>bottom</em> edges. * + * <h4>Interpretation of GONE</h4> + * + * For layout purposes, GridLayout treats views whose visibility status is + * {@link View#GONE GONE}, as having zero width and height. This is subtly different from + * the policy of ignoring views that are marked as GONE outright. If, for example, a gone-marked + * view was alone in a column, that column would itself collapse to zero width if and only if + * no gravity was defined on the view. If gravity was defined, then the gone-marked + * view has no effect on the layout and the container should be laid out as if the view + * had never been added to it. + * These statements apply equally to rows as well as columns, and to groups of rows or columns. + * * <h5>Limitations</h5> * * GridLayout does not provide support for the principle of <em>weight</em>, as defined in @@ -208,10 +221,15 @@ public class GridLayout extends ViewGroup { // Misc constants - static final String TAG = GridLayout.class.getName(); static final int MAX_SIZE = 100000; static final int DEFAULT_CONTAINER_MARGIN = 0; static final int UNINITIALIZED_HASH = 0; + static final Printer LOG_PRINTER = new LogPrinter(Log.DEBUG, GridLayout.class.getName()); + static final Printer NO_PRINTER = new Printer() { + @Override + public void println(String x) { + } + }; // Defaults @@ -233,13 +251,14 @@ public class GridLayout extends ViewGroup { // Instance variables - final Axis horizontalAxis = new Axis(true); - final Axis verticalAxis = new Axis(false); - int orientation = DEFAULT_ORIENTATION; - boolean useDefaultMargins = DEFAULT_USE_DEFAULT_MARGINS; - int alignmentMode = DEFAULT_ALIGNMENT_MODE; - int defaultGap; - int lastLayoutParamsHashCode = UNINITIALIZED_HASH; + final Axis mHorizontalAxis = new Axis(true); + final Axis mVerticalAxis = new Axis(false); + int mOrientation = DEFAULT_ORIENTATION; + boolean mUseDefaultMargins = DEFAULT_USE_DEFAULT_MARGINS; + int mAlignmentMode = DEFAULT_ALIGNMENT_MODE; + int mDefaultGap; + int mLastLayoutParamsHashCode = UNINITIALIZED_HASH; + Printer mPrinter = LOG_PRINTER; // Constructors @@ -248,7 +267,7 @@ public class GridLayout extends ViewGroup { */ public GridLayout(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); - defaultGap = context.getResources().getDimensionPixelOffset(R.dimen.default_gap); + mDefaultGap = context.getResources().getDimensionPixelOffset(R.dimen.default_gap); TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.GridLayout); try { setRowCount(a.getInt(ROW_COUNT, DEFAULT_COUNT)); @@ -290,7 +309,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_orientation */ public int getOrientation() { - return orientation; + return mOrientation; } /** @@ -330,8 +349,8 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_orientation */ public void setOrientation(int orientation) { - if (this.orientation != orientation) { - this.orientation = orientation; + if (this.mOrientation != orientation) { + this.mOrientation = orientation; invalidateStructure(); requestLayout(); } @@ -350,7 +369,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_rowCount */ public int getRowCount() { - return verticalAxis.getCount(); + return mVerticalAxis.getCount(); } /** @@ -365,7 +384,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_rowCount */ public void setRowCount(int rowCount) { - verticalAxis.setCount(rowCount); + mVerticalAxis.setCount(rowCount); invalidateStructure(); requestLayout(); } @@ -383,7 +402,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_columnCount */ public int getColumnCount() { - return horizontalAxis.getCount(); + return mHorizontalAxis.getCount(); } /** @@ -398,7 +417,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_columnCount */ public void setColumnCount(int columnCount) { - horizontalAxis.setCount(columnCount); + mHorizontalAxis.setCount(columnCount); invalidateStructure(); requestLayout(); } @@ -414,7 +433,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_useDefaultMargins */ public boolean getUseDefaultMargins() { - return useDefaultMargins; + return mUseDefaultMargins; } /** @@ -444,7 +463,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_useDefaultMargins */ public void setUseDefaultMargins(boolean useDefaultMargins) { - this.useDefaultMargins = useDefaultMargins; + this.mUseDefaultMargins = useDefaultMargins; requestLayout(); } @@ -461,7 +480,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_alignmentMode */ public int getAlignmentMode() { - return alignmentMode; + return mAlignmentMode; } /** @@ -480,7 +499,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_alignmentMode */ public void setAlignmentMode(int alignmentMode) { - this.alignmentMode = alignmentMode; + this.mAlignmentMode = alignmentMode; requestLayout(); } @@ -495,7 +514,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_rowOrderPreserved */ public boolean isRowOrderPreserved() { - return verticalAxis.isOrderPreserved(); + return mVerticalAxis.isOrderPreserved(); } /** @@ -515,7 +534,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_rowOrderPreserved */ public void setRowOrderPreserved(boolean rowOrderPreserved) { - verticalAxis.setOrderPreserved(rowOrderPreserved); + mVerticalAxis.setOrderPreserved(rowOrderPreserved); invalidateStructure(); requestLayout(); } @@ -531,7 +550,7 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_columnOrderPreserved */ public boolean isColumnOrderPreserved() { - return horizontalAxis.isOrderPreserved(); + return mHorizontalAxis.isOrderPreserved(); } /** @@ -551,11 +570,38 @@ public class GridLayout extends ViewGroup { * @attr ref android.R.styleable#GridLayout_columnOrderPreserved */ public void setColumnOrderPreserved(boolean columnOrderPreserved) { - horizontalAxis.setOrderPreserved(columnOrderPreserved); + mHorizontalAxis.setOrderPreserved(columnOrderPreserved); invalidateStructure(); requestLayout(); } + /** + * Return the printer that will log diagnostics from this layout. + * + * @see #setPrinter(android.util.Printer) + * + * @return the printer associated with this view + * + * @hide + */ + public Printer getPrinter() { + return mPrinter; + } + + /** + * Set the printer that will log diagnostics from this layout. + * The default value is created by {@link android.util.LogPrinter}. + * + * @param printer the printer associated with this layout + * + * @see #getPrinter() + * + * @hide + */ + public void setPrinter(Printer printer) { + this.mPrinter = (printer == null) ? NO_PRINTER : printer; + } + // Static utility methods static int max2(int[] a, int valueIfEmpty) { @@ -601,7 +647,7 @@ public class GridLayout extends ViewGroup { if (c.getClass() == Space.class) { return 0; } - return defaultGap / 2; + return mDefaultGap / 2; } private int getDefaultMargin(View c, boolean isAtEdge, boolean horizontal, boolean leading) { @@ -609,11 +655,11 @@ public class GridLayout extends ViewGroup { } private int getDefaultMargin(View c, LayoutParams p, boolean horizontal, boolean leading) { - if (!useDefaultMargins) { + if (!mUseDefaultMargins) { return 0; } Spec spec = horizontal ? p.columnSpec : p.rowSpec; - Axis axis = horizontal ? horizontalAxis : verticalAxis; + Axis axis = horizontal ? mHorizontalAxis : mVerticalAxis; Interval span = spec.span; boolean leading1 = (horizontal && isLayoutRtl()) ? !leading : leading; boolean isAtEdge = leading1 ? (span.min == 0) : (span.max == axis.getCount()); @@ -630,10 +676,10 @@ public class GridLayout extends ViewGroup { } private int getMargin(View view, boolean horizontal, boolean leading) { - if (alignmentMode == ALIGN_MARGINS) { + if (mAlignmentMode == ALIGN_MARGINS) { return getMargin1(view, horizontal, leading); } else { - Axis axis = horizontal ? horizontalAxis : verticalAxis; + Axis axis = horizontal ? mHorizontalAxis : mVerticalAxis; int[] margins = leading ? axis.getLeadingMargins() : axis.getTrailingMargins(); LayoutParams lp = getLayoutParams(view); Spec spec = horizontal ? lp.columnSpec : lp.rowSpec; @@ -680,8 +726,8 @@ public class GridLayout extends ViewGroup { // install default indices for cells that don't define them private void validateLayoutParams() { - final boolean horizontal = (orientation == HORIZONTAL); - final Axis axis = horizontal ? horizontalAxis : verticalAxis; + final boolean horizontal = (mOrientation == HORIZONTAL); + final Axis axis = horizontal ? mHorizontalAxis : mVerticalAxis; final int count = (axis.definedCount != UNDEFINED) ? axis.definedCount : 0; int major = 0; @@ -737,9 +783,9 @@ public class GridLayout extends ViewGroup { } private void invalidateStructure() { - lastLayoutParamsHashCode = UNINITIALIZED_HASH; - horizontalAxis.invalidateStructure(); - verticalAxis.invalidateStructure(); + mLastLayoutParamsHashCode = UNINITIALIZED_HASH; + mHorizontalAxis.invalidateStructure(); + mVerticalAxis.invalidateStructure(); // This can end up being done twice. Better twice than not at all. invalidateValues(); } @@ -747,9 +793,9 @@ public class GridLayout extends ViewGroup { private void invalidateValues() { // Need null check because requestLayout() is called in View's initializer, // before we are set up. - if (horizontalAxis != null && verticalAxis != null) { - horizontalAxis.invalidateValues(); - verticalAxis.invalidateValues(); + if (mHorizontalAxis != null && mVerticalAxis != null) { + mHorizontalAxis.invalidateValues(); + mVerticalAxis.invalidateValues(); } } @@ -780,7 +826,7 @@ public class GridLayout extends ViewGroup { if (span.min != UNDEFINED && span.min < 0) { handleInvalidParams(groupName + " indices must be positive"); } - Axis axis = horizontal ? horizontalAxis : verticalAxis; + Axis axis = horizontal ? mHorizontalAxis : mVerticalAxis; int count = axis.definedCount; if (count != UNDEFINED) { if (span.max > count) { @@ -866,7 +912,7 @@ public class GridLayout extends ViewGroup { int right = getWidth() - getPaddingRight() - insets.right; int bottom = getHeight() - getPaddingBottom() - insets.bottom; - int[] xs = horizontalAxis.locations; + int[] xs = mHorizontalAxis.locations; if (xs != null) { for (int i = 0, length = xs.length; i < length; i++) { int x = left + xs[i]; @@ -874,7 +920,7 @@ public class GridLayout extends ViewGroup { } } - int[] ys = verticalAxis.locations; + int[] ys = mVerticalAxis.locations; if (ys != null) { for (int i = 0, length = ys.length; i < length; i++) { int y = top + ys[i]; @@ -915,7 +961,7 @@ public class GridLayout extends ViewGroup { protected void onChildVisibilityChanged(View child, int oldVisibility, int newVisibility) { super.onChildVisibilityChanged(child, oldVisibility, newVisibility); if (oldVisibility == GONE || newVisibility == GONE) { - invalidateStructure(); + invalidateStructure(); } } @@ -931,12 +977,12 @@ public class GridLayout extends ViewGroup { } private void consistencyCheck() { - if (lastLayoutParamsHashCode == UNINITIALIZED_HASH) { + if (mLastLayoutParamsHashCode == UNINITIALIZED_HASH) { validateLayoutParams(); - lastLayoutParamsHashCode = computeLayoutParamsHashCode(); - } else if (lastLayoutParamsHashCode != computeLayoutParamsHashCode()) { - Log.w(TAG, "The fields of some layout parameters were modified in between layout " + - "operations. Check the javadoc for GridLayout.LayoutParams#rowSpec."); + mLastLayoutParamsHashCode = computeLayoutParamsHashCode(); + } else if (mLastLayoutParamsHashCode != computeLayoutParamsHashCode()) { + mPrinter.println("The fields of some layout parameters were modified in between " + + "layout operations. Check the javadoc for GridLayout.LayoutParams#rowSpec."); invalidateStructure(); consistencyCheck(); } @@ -963,11 +1009,11 @@ public class GridLayout extends ViewGroup { if (firstPass) { measureChildWithMargins2(c, widthSpec, heightSpec, lp.width, lp.height); } else { - boolean horizontal = (orientation == HORIZONTAL); + boolean horizontal = (mOrientation == HORIZONTAL); Spec spec = horizontal ? lp.columnSpec : lp.rowSpec; if (spec.alignment == FILL) { Interval span = spec.span; - Axis axis = horizontal ? horizontalAxis : verticalAxis; + Axis axis = horizontal ? mHorizontalAxis : mVerticalAxis; int[] locations = axis.getLocations(); int cellSize = locations[span.max] - locations[span.min]; int viewSize = cellSize - getTotalMargin(c, horizontal); @@ -1006,14 +1052,14 @@ public class GridLayout extends ViewGroup { int heightSansPadding; // Use the orientation property to decide which axis should be laid out first. - if (orientation == HORIZONTAL) { - widthSansPadding = horizontalAxis.getMeasure(widthSpecSansPadding); + if (mOrientation == HORIZONTAL) { + widthSansPadding = mHorizontalAxis.getMeasure(widthSpecSansPadding); measureChildrenWithMargins(widthSpecSansPadding, heightSpecSansPadding, false); - heightSansPadding = verticalAxis.getMeasure(heightSpecSansPadding); + heightSansPadding = mVerticalAxis.getMeasure(heightSpecSansPadding); } else { - heightSansPadding = verticalAxis.getMeasure(heightSpecSansPadding); + heightSansPadding = mVerticalAxis.getMeasure(heightSpecSansPadding); measureChildrenWithMargins(widthSpecSansPadding, heightSpecSansPadding, false); - widthSansPadding = horizontalAxis.getMeasure(widthSpecSansPadding); + widthSansPadding = mHorizontalAxis.getMeasure(widthSpecSansPadding); } int measuredWidth = Math.max(widthSansPadding + hPadding, getSuggestedMinimumWidth()); @@ -1072,11 +1118,11 @@ public class GridLayout extends ViewGroup { int paddingRight = getPaddingRight(); int paddingBottom = getPaddingBottom(); - horizontalAxis.layout(targetWidth - paddingLeft - paddingRight); - verticalAxis.layout(targetHeight - paddingTop - paddingBottom); + mHorizontalAxis.layout(targetWidth - paddingLeft - paddingRight); + mVerticalAxis.layout(targetHeight - paddingTop - paddingBottom); - int[] hLocations = horizontalAxis.getLocations(); - int[] vLocations = verticalAxis.getLocations(); + int[] hLocations = mHorizontalAxis.getLocations(); + int[] vLocations = mVerticalAxis.getLocations(); for (int i = 0, N = getChildCount(); i < N; i++) { View c = getChildAt(i); @@ -1103,8 +1149,8 @@ public class GridLayout extends ViewGroup { Alignment hAlign = getAlignment(columnSpec.alignment, true); Alignment vAlign = getAlignment(rowSpec.alignment, false); - Bounds boundsX = horizontalAxis.getGroupBounds().getValue(i); - Bounds boundsY = verticalAxis.getGroupBounds().getValue(i); + Bounds boundsX = mHorizontalAxis.getGroupBounds().getValue(i); + Bounds boundsY = mVerticalAxis.getGroupBounds().getValue(i); // Gravity offsets: the location of the alignment group relative to its cell group. int gravityOffsetX = hAlign.getGravityOffset(c, cellWidth - boundsX.size(true)); @@ -1246,6 +1292,7 @@ public class GridLayout extends ViewGroup { Assoc<Spec, Bounds> assoc = Assoc.of(Spec.class, Bounds.class); for (int i = 0, N = getChildCount(); i < N; i++) { View c = getChildAt(i); + // we must include views that are GONE here, see introductory javadoc LayoutParams lp = getLayoutParams(c); Spec spec = horizontal ? lp.columnSpec : lp.rowSpec; Bounds bounds = getAlignment(spec.alignment, horizontal).getBounds(); @@ -1261,6 +1308,7 @@ public class GridLayout extends ViewGroup { } for (int i = 0, N = getChildCount(); i < N; i++) { View c = getChildAt(i); + // we must include views that are GONE here, see introductory javadoc LayoutParams lp = getLayoutParams(c); Spec spec = horizontal ? lp.columnSpec : lp.rowSpec; groupBounds.getValue(i).include(GridLayout.this, c, spec, this); @@ -1527,8 +1575,8 @@ public class GridLayout extends ViewGroup { removed.add(arc); } } - Log.d(TAG, axisName + " constraints: " + arcsToString(culprits) + " are inconsistent; " - + "permanently removing: " + arcsToString(removed) + ". "); + mPrinter.println(axisName + " constraints: " + arcsToString(culprits) + + " are inconsistent; permanently removing: " + arcsToString(removed) + ". "); } /* @@ -1917,12 +1965,16 @@ public class GridLayout extends ViewGroup { } /** - * {@inheritDoc} + * Copy constructor. Clones the width, height, margin values, row spec, + * and column spec of the source. + * + * @param source The layout params to copy from. */ - public LayoutParams(LayoutParams that) { - super(that); - this.rowSpec = that.rowSpec; - this.columnSpec = that.columnSpec; + public LayoutParams(LayoutParams source) { + super(source); + + this.rowSpec = source.rowSpec; + this.columnSpec = source.columnSpec; } // AttributeSet constructors @@ -2666,6 +2718,9 @@ public class GridLayout extends ViewGroup { @Override public int getAlignmentValue(View view, int viewSize, int mode) { + if (view.getVisibility() == GONE) { + return 0; + } int baseline = view.getBaseline(); return baseline == -1 ? UNDEFINED : baseline; } |
