-
Notifications
You must be signed in to change notification settings - Fork 7
/
AutoGridView.java
133 lines (113 loc) · 3.46 KB
/
AutoGridView.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
package nl.obduro.views;
import android.content.Context;
import android.content.res.Configuration;
import android.util.AttributeSet;
import android.util.Log;
import android.view.View;
import android.widget.GridView;
import android.widget.ListAdapter;
/**
* Automatically calculates the ideal for each row
* @author JJ
*
*/
public class AutoGridView extends GridView {
private static final String TAG = "AutoGridView";
private int numColumnsID;
private int previousFirstVisible;
private int numColumns = 1;
public AutoGridView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
init(attrs);
}
public AutoGridView(Context context, AttributeSet attrs) {
super(context, attrs);
init(attrs);
}
public AutoGridView(Context context) {
super(context);
}
/**
* Sets the numColumns based on the attributeset
*/
private void init(AttributeSet attrs) {
// Read numColumns out of the AttributeSet
int count = attrs.getAttributeCount();
if(count > 0) {
for(int i = 0; i < count; i++) {
String name = attrs.getAttributeName(i);
if(name != null && name.equals("numColumns")) {
// Update columns
this.numColumnsID = attrs.getAttributeResourceValue(i, 1);
updateColumns();
break;
}
}
}
Log.d(TAG, "numColumns set to: " + numColumns);
}
/**
* Reads the amount of columns from the resource file and
* updates the "numColumns" variable
*/
private void updateColumns() {
this.numColumns = getContext().getResources().getInteger(numColumnsID);
}
@Override
public void setNumColumns(int numColumns) {
this.numColumns = numColumns;
super.setNumColumns(numColumns);
Log.d(TAG, "setSelection --> " + previousFirstVisible);
setSelection(previousFirstVisible);
}
@Override
protected void onLayout(boolean changed, int leftPos, int topPos, int rightPos, int bottomPos) {
super.onLayout(changed, leftPos, topPos, rightPos, bottomPos);
setHeights();
}
@Override
protected void onConfigurationChanged(Configuration newConfig) {
updateColumns();
setNumColumns(this.numColumns);
}
@Override
protected void onScrollChanged(int newHorizontal, int newVertical, int oldHorizontal, int oldVertical) {
// Check if the first visible position has changed due to this scroll
int firstVisible = getFirstVisiblePosition();
if(previousFirstVisible != firstVisible) {
// Update position, and update heights
previousFirstVisible = firstVisible;
setHeights();
}
super.onScrollChanged(newHorizontal, newVertical, oldHorizontal, oldVertical);
}
/**
* Sets the height of each view in a row equal to the height of the tallest view in this row.
* @param firstVisible The first visible position (adapter order)
*/
private void setHeights() {
ListAdapter adapter = getAdapter();
if(adapter != null) {
for(int i = 0; i < getChildCount(); i+=numColumns) {
// Determine the maximum height for this row
int maxHeight = 0;
for(int j = i; j < i+numColumns; j++) {
View view = getChildAt(j);
if(view != null && view.getHeight() > maxHeight) {
maxHeight = view.getHeight();
}
}
//Log.d(TAG, "Max height for row #" + i/numColumns + ": " + maxHeight);
// Set max height for each element in this row
if(maxHeight > 0) {
for(int j = i; j < i+numColumns; j++) {
View view = getChildAt(j);
if(view != null && view.getHeight() != maxHeight) {
view.setMinimumHeight(maxHeight);
}
}
}
}
}
}
}