160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov/* 260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Copyright (C) 2010 The Android Open Source Project 360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * 460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Licensed under the Apache License, Version 2.0 (the "License"); 560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * you may not use this file except in compliance with the License. 660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * You may obtain a copy of the License at 760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * 860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * http://www.apache.org/licenses/LICENSE-2.0 960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * 1060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Unless required by applicable law or agreed to in writing, software 1160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * distributed under the License is distributed on an "AS IS" BASIS, 1260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * See the License for the specific language governing permissions and 1460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * limitations under the License. 1560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 1660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovpackage com.android.common.widget; 1760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 1860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovimport android.content.Context; 1960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovimport android.database.Cursor; 2060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovimport android.view.View; 2160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovimport android.view.ViewGroup; 2260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovimport android.widget.BaseAdapter; 2360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 249a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albertimport java.util.ArrayList; 259a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert 2660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov/** 2760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * A general purpose adapter that is composed of multiple cursors. It just 2860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * appends them in the order they are added. 2960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 3060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikovpublic abstract class CompositeCursorAdapter extends BaseAdapter { 3160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 3260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov private static final int INITIAL_CAPACITY = 2; 3360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 3460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public static class Partition { 3560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov boolean showIfEmpty; 3660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov boolean hasHeader; 3760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 3860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov Cursor cursor; 3960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int idColumnIndex; 4060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int count; 4160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 4260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public Partition(boolean showIfEmpty, boolean hasHeader) { 4360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov this.showIfEmpty = showIfEmpty; 4460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov this.hasHeader = hasHeader; 4560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 4660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 4760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 4860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * True if the directory should be shown even if no contacts are found. 4960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 5060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public boolean getShowIfEmpty() { 5160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return showIfEmpty; 5260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 5360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 5460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public boolean getHasHeader() { 5560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return hasHeader; 5660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 5760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 5860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 5960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov private final Context mContext; 609a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert private ArrayList<Partition> mPartitions; 6160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov private int mCount = 0; 6260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov private boolean mCacheValid = true; 6355f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov private boolean mNotificationsEnabled = true; 6455f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov private boolean mNotificationNeeded; 6560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 6660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public CompositeCursorAdapter(Context context) { 6760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov this(context, INITIAL_CAPACITY); 6860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 6960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 7060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public CompositeCursorAdapter(Context context, int initialCapacity) { 7160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov mContext = context; 729a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions = new ArrayList<Partition>(); 7360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 7460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 7560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public Context getContext() { 7660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return mContext; 7760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 7860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 7960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 8060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Registers a partition. The cursor for that partition can be set later. 8160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Partitions should be added in the order they are supposed to appear in the 8260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * list. 8360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 8460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void addPartition(boolean showIfEmpty, boolean hasHeader) { 8560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov addPartition(new Partition(showIfEmpty, hasHeader)); 8660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 8760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 8860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void addPartition(Partition partition) { 899a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.add(partition); 909a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert invalidate(); 919a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert notifyDataSetChanged(); 929a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert } 939a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert 949a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert public void addPartition(int location, Partition partition) { 959a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.add(location, partition); 9660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov invalidate(); 9760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov notifyDataSetChanged(); 9860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 9960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 10060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void removePartition(int partitionIndex) { 1019a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor cursor = mPartitions.get(partitionIndex).cursor; 10260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (cursor != null && !cursor.isClosed()) { 10360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov cursor.close(); 10460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 1059a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.remove(partitionIndex); 10660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov invalidate(); 10760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov notifyDataSetChanged(); 10860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 10960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 11060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 11160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Removes cursors for all partitions. 11260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 1139a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert // TODO: Is this really what this is supposed to do? Just remove the cursors? Not close them? 1149a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert // Not remove the partitions themselves? Isn't this leaking? 1159a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert 11660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void clearPartitions() { 1179a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition partition : mPartitions) { 1189a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert partition.cursor = null; 11960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 12060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov invalidate(); 12160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov notifyDataSetChanged(); 12260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 12360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 1245cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov /** 1255cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov * Closes all cursors and removes all partitions. 1265cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov */ 1275cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov public void close() { 1289a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition partition : mPartitions) { 1299a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor cursor = partition.cursor; 1305cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov if (cursor != null && !cursor.isClosed()) { 1315cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov cursor.close(); 1325cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov } 1335cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov } 1349a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.clear(); 1355cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov invalidate(); 1365cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov notifyDataSetChanged(); 1375cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov } 1385cc774535d73c09b6788b63ecc728e60da09cfa9Dmitri Plotnikov 13960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void setHasHeader(int partitionIndex, boolean flag) { 1409a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.get(partitionIndex).hasHeader = flag; 14160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov invalidate(); 14260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 14360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 14460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void setShowIfEmpty(int partitionIndex, boolean flag) { 1459a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.get(partitionIndex).showIfEmpty = flag; 14660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov invalidate(); 14760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 14860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 14960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public Partition getPartition(int partitionIndex) { 1509a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert return mPartitions.get(partitionIndex); 15160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 15260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 15360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected void invalidate() { 15460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov mCacheValid = false; 15560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 15660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 15760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getPartitionCount() { 1589a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert return mPartitions.size(); 15960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 16060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 16160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected void ensureCacheValid() { 16260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (mCacheValid) { 16360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return; 16460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 16560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 16660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov mCount = 0; 1679a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition partition : mPartitions) { 1689a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor cursor = partition.cursor; 16960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int count = cursor != null ? cursor.getCount() : 0; 1709a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (partition.hasHeader) { 1719a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (count != 0 || partition.showIfEmpty) { 17260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov count++; 17360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 17460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 1759a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert partition.count = count; 17660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov mCount += count; 17760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 17860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 17960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov mCacheValid = true; 18060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 18160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 18260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 18360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns true if the specified partition was configured to have a header. 18460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 18560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public boolean hasHeader(int partition) { 1869a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert return mPartitions.get(partition).hasHeader; 18760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 18860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 18960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 19060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the total number of list items in all partitions. 19160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 19260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getCount() { 19360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 19460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return mCount; 19560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 19660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 19760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 19860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the cursor for the given partition 19960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 20060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public Cursor getCursor(int partition) { 2019a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert return mPartitions.get(partition).cursor; 20260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 20360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 20460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 20560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Changes the cursor for an individual partition. 20660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 20760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public void changeCursor(int partition, Cursor cursor) { 2089a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor prevCursor = mPartitions.get(partition).cursor; 20960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (prevCursor != cursor) { 21060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (prevCursor != null && !prevCursor.isClosed()) { 21160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov prevCursor.close(); 21260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 2139a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.get(partition).cursor = cursor; 21460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (cursor != null) { 2159a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert mPartitions.get(partition).idColumnIndex = cursor.getColumnIndex("_id"); 21660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 21760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov invalidate(); 21860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov notifyDataSetChanged(); 21960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 22060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 22160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 22260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 22360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns true if the specified partition has no cursor or an empty cursor. 22460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 22560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public boolean isPartitionEmpty(int partition) { 2269a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor cursor = mPartitions.get(partition).cursor; 22760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return cursor == null || cursor.getCount() == 0; 22860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 22960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 23060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 23160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Given a list position, returns the index of the corresponding partition. 23260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 23360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getPartitionForPosition(int position) { 23460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 23560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 2369a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (int i = 0, n = mPartitions.size(); i < n; i++) { 2379a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + mPartitions.get(i).count; 23860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 23960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return i; 24060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 24160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 24260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 24360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return -1; 24460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 24560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 24660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 24760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Given a list position, return the offset of the corresponding item in its 24860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * partition. The header, if any, will have offset -1. 24960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 25060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getOffsetInPartition(int position) { 25160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 25260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 2539a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition partition : mPartitions) { 2549a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + partition.count; 25560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 25660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int offset = position - start; 2579a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (partition.hasHeader) { 25860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov offset--; 25960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 26060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return offset; 26160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 26260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 26360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 26460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return -1; 26560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 26660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 26760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 26860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the first list position for the specified partition. 26960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 27060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getPositionForPartition(int partition) { 27160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 27260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int position = 0; 27360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov for (int i = 0; i < partition; i++) { 2749a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert position += mPartitions.get(i).count; 27560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 27660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return position; 27760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 27860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 27960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov @Override 28060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getViewTypeCount() { 28160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return getItemViewTypeCount() + 1; 28260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 28360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 28460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 28560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the overall number of item view types across all partitions. An 28660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * implementation of this method needs to ensure that the returned count is 28760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * consistent with the values returned by {@link #getItemViewType(int,int)}. 28860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 28960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getItemViewTypeCount() { 29060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return 1; 29160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 29260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 29360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 29460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the view type for the list item at the specified position in the 29560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * specified partition. 29660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 29760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected int getItemViewType(int partition, int position) { 29860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return 1; 29960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 30060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 30160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov @Override 30260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public int getItemViewType(int position) { 30360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 30460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 3059a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (int i = 0, n = mPartitions.size(); i < n; i++) { 3069a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + mPartitions.get(i).count; 30760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 30860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int offset = position - start; 3099a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartitions.get(i).hasHeader) { 31053f35c7c31f31db40b106cc0f7a51f5daf40a7fdYorke Lee offset--; 31153f35c7c31f31db40b106cc0f7a51f5daf40a7fdYorke Lee } 31253f35c7c31f31db40b106cc0f7a51f5daf40a7fdYorke Lee if (offset == -1) { 31360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return IGNORE_ITEM_VIEW_TYPE; 31453f35c7c31f31db40b106cc0f7a51f5daf40a7fdYorke Lee } else { 31553f35c7c31f31db40b106cc0f7a51f5daf40a7fdYorke Lee return getItemViewType(i, offset); 31660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 31760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 31860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 31960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 32060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 32160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov throw new ArrayIndexOutOfBoundsException(position); 32260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 32360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 32460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public View getView(int position, View convertView, ViewGroup parent) { 32560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 32660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 3279a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (int i = 0, n = mPartitions.size(); i < n; i++) { 3289a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + mPartitions.get(i).count; 32960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 33060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int offset = position - start; 3319a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartitions.get(i).hasHeader) { 33260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov offset--; 33360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 33460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov View view; 33560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (offset == -1) { 3369a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert view = getHeaderView(i, mPartitions.get(i).cursor, convertView, parent); 33760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } else { 3389a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (!mPartitions.get(i).cursor.moveToPosition(offset)) { 33960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov throw new IllegalStateException("Couldn't move cursor to position " 34060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov + offset); 34160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 3429a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert view = getView(i, mPartitions.get(i).cursor, offset, convertView, parent); 34360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 34460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (view == null) { 34560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov throw new NullPointerException("View should not be null, partition: " + i 34660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov + " position: " + offset); 34760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 34860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return view; 34960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 35060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 35160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 35260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 35360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov throw new ArrayIndexOutOfBoundsException(position); 35460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 35560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 35660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 35760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the header view for the specified partition, creating one if needed. 35860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 35960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected View getHeaderView(int partition, Cursor cursor, View convertView, 36060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ViewGroup parent) { 36160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov View view = convertView != null 36260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ? convertView 36360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov : newHeaderView(mContext, partition, cursor, parent); 36460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov bindHeaderView(view, partition, cursor); 36560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return view; 36660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 36760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 36860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 36960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Creates the header view for the specified partition. 37060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 37160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected View newHeaderView(Context context, int partition, Cursor cursor, 37260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ViewGroup parent) { 37360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return null; 37460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 37560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 37660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 37760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Binds the header view for the specified partition. 37860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 37960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected void bindHeaderView(View view, int partition, Cursor cursor) { 38060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 38160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 38260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 38360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns an item view for the specified partition, creating one if needed. 38460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 38560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected View getView(int partition, Cursor cursor, int position, View convertView, 38660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ViewGroup parent) { 38760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov View view; 38860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (convertView != null) { 38960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov view = convertView; 39060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } else { 39160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov view = newView(mContext, partition, cursor, position, parent); 39260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 39360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov bindView(view, partition, cursor, position); 39460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return view; 39560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 39660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 39760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 39860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Creates an item view for the specified partition and position. Position 39960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * corresponds directly to the current cursor position. 40060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 40160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected abstract View newView(Context context, int partition, Cursor cursor, int position, 40260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ViewGroup parent); 40360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 40460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 40560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Binds an item view for the specified partition and position. Position 40660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * corresponds directly to the current cursor position. 40760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 40860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected abstract void bindView(View v, int partition, Cursor cursor, int position); 40960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 41060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 41160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns a pre-positioned cursor for the specified list position. 41260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 41360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public Object getItem(int position) { 41460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 41560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 4169a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition mPartition : mPartitions) { 4179a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + mPartition.count; 41860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 41960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int offset = position - start; 4209a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartition.hasHeader) { 42160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov offset--; 42260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 42360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (offset == -1) { 42460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return null; 42560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 4269a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor cursor = mPartition.cursor; 42760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov cursor.moveToPosition(offset); 42860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return cursor; 42960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 43060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 43160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 43260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 43360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return null; 43460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 43560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 43660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 43760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns the item ID for the specified list position. 43860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 43960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public long getItemId(int position) { 44060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 44160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 4429a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition mPartition : mPartitions) { 4439a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + mPartition.count; 44460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 44560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int offset = position - start; 4469a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartition.hasHeader) { 44760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov offset--; 44860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 44960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (offset == -1) { 45060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return 0; 45160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 4529a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartition.idColumnIndex == -1) { 45360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return 0; 45460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 45560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 4569a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert Cursor cursor = mPartition.cursor; 45760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (cursor == null || cursor.isClosed() || !cursor.moveToPosition(offset)) { 45860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return 0; 45960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 4609a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert return cursor.getLong(mPartition.idColumnIndex); 46160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 46260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 46360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 46460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 46560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return 0; 46660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 46760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 46860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 46960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns false if any partition has a header. 47060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 47160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov @Override 47260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public boolean areAllItemsEnabled() { 4739a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (Partition mPartition : mPartitions) { 4749a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartition.hasHeader) { 47560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return false; 47660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 47760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 47860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return true; 47960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 48060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 48160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 48260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns true for all items except headers. 48360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 48460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov @Override 48560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov public boolean isEnabled(int position) { 48660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov ensureCacheValid(); 48760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int start = 0; 4889a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert for (int i = 0, n = mPartitions.size(); i < n; i++) { 4899a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert int end = start + mPartitions.get(i).count; 49060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov if (position >= start && position < end) { 49160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov int offset = position - start; 4929a4f02a8eaf7eb3991900231dbea250e4fb34553Alon Albert if (mPartitions.get(i).hasHeader && offset == 0) { 49360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return false; 49460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } else { 49560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return isEnabled(i, offset); 49660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 49760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 49860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov start = end; 49960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 50060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 50160ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return false; 50260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 50360ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov 50460ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov /** 50560ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * Returns true if the item at the specified offset of the specified 50660ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov * partition is selectable and clickable. 50760ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov */ 50860ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov protected boolean isEnabled(int partition, int position) { 50960ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov return true; 51060ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov } 51155f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov 51255f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov /** 51355f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov * Enable or disable data change notifications. It may be a good idea to 51455f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov * disable notifications before making changes to several partitions at once. 51555f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov */ 51655f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov public void setNotificationsEnabled(boolean flag) { 5177c76d5f2cd2cc35e7c4f33264d5f281c96351377Gilles Debunne mNotificationsEnabled = flag; 5187c76d5f2cd2cc35e7c4f33264d5f281c96351377Gilles Debunne if (flag && mNotificationNeeded) { 51955f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov notifyDataSetChanged(); 52055f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov } 52155f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov } 52255f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov 52355f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov @Override 52455f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov public void notifyDataSetChanged() { 52555f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov if (mNotificationsEnabled) { 52655f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov mNotificationNeeded = false; 52755f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov super.notifyDataSetChanged(); 52855f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov } else { 52955f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov mNotificationNeeded = true; 53055f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov } 53155f04311fb40ccadb224f1a4dc1b8ff473dfdf03Dmitri Plotnikov } 53260ae52719e0567fa5b1860df19807716951eca50Dmitri Plotnikov} 533