/* * Copyright (C) 2006 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package android.widget; import android.content.Context; import android.database.Cursor; import android.net.Uri; import android.view.View; /** * 用于将游标列映射到XML文件中定义的文本视图或图像视图的简单适配器. * 你可以指定有哪些列,由那些视图显示这些列的内容,并通过XML定义这些视图的呈现. * 可以为分组和子视图分别指定XML文件. * * 绑定由两个阶段组成.首先,如果 * {@link android.widget.SimpleCursorTreeAdapter.ViewBinder}可用,则执行 * {@link ViewBinder#setViewValue(android.view.View, android.database.Cursor, int)}. * 如果返回在为真,代表发生了绑定.如果返回值为假,并且要绑定的是文本视图,则执行 * {@link #setViewText(TextView, String)} 方法.如果返回值为假,并且要绑定的是 * ImageView,则执行{@link #setViewImage(ImageView, String)}.如果没有适当的绑定发生, * 将抛出{@link IllegalStateException}. */ public abstract class SimpleCursorTreeAdapter extends ResourceCursorTreeAdapter { /** The name of the columns that contain the data to display for a group. */ private String[] mGroupFromNames; /** The indices of columns that contain data to display for a group. */ private int[] mGroupFrom; /** * The View IDs that will display a group's data fetched from the * corresponding column. */ private int[] mGroupTo; /** The name of the columns that contain the data to display for a child. */ private String[] mChildFromNames; /** The indices of columns that contain data to display for a child. */ private int[] mChildFrom; /** * The View IDs that will display a child's data fetched from the * corresponding column. */ private int[] mChildTo; /** * View binder, if supplied */ private ViewBinder mViewBinder; /** * 构造函数 * * @param context 运行时,与 {@link SimpleCursorTreeAdapter} * 关联的 {@link ExpandableListView} 的上下文. * @param cursor 数据库游标 * @param collapsedGroupLayout 定义组收起时视图的XML资源布局. * 该布局文件应当至少包括所有在groupTo中所定义的视图. * @param expandedGroupLayout 定义组展开时视图的XML资源布局. * 该布局文件应当至少包括所有在groupTo中所定义的视图. * @param groupFrom 在组中显示的数据的列名. * @param groupTo 用于显示“from”参数中的列内容的分组视图(来自分组布局). * 这些视图应该都是文本视图或图像视图.视图与列一一对应. * @param childLayout 布局资源文件标识,其定义的是子视图的布局样式 * (不包括最后一个子视图),内部至少要包含参数 “childTo”中指定的视图ID. * @param lastChildLayout 布局资源文件标识,其定义的是最后一个子视图的布局文件. * 该布局文件至少要包含参数“childTo”中定义的视图ID. * @param childFrom 用于子视图显示的数据的列名列表. * @param childTo 用于显示“from”参数中指定列的子视图(来自子布局文件). * 这些视图应该都为文本视图或图像视图.视图与给定参数列的顺序是一一对应的. */ public SimpleCursorTreeAdapter(Context context, Cursor cursor, int collapsedGroupLayout, int expandedGroupLayout, String[] groupFrom, int[] groupTo, int childLayout, int lastChildLayout, String[] childFrom, int[] childTo) { super(context, cursor, collapsedGroupLayout, expandedGroupLayout, childLayout, lastChildLayout); init(groupFrom, groupTo, childFrom, childTo); } /** * 构造函数 * * @param context 运行时,与 {@link SimpleCursorTreeAdapter} * 关联的 {@link ExpandableListView} 的上下文. * @param cursor 数据库游标 * @param collapsedGroupLayout 定义组收起时视图的XML资源布局. * 该布局文件应当至少包括所有在groupTo中所定义的视图. * @param expandedGroupLayout 定义组展开时视图的XML资源布局. * 该布局文件应当至少包括所有在groupTo中所定义的视图. * @param groupFrom 在组中显示的数据的列名. * @param groupTo 用于显示“from”参数中的列内容的分组视图(来自分组布局). * 这些视图应该都是文本视图或图像视图.视图与列一一对应. * @param childLayout 布局资源文件标识ID,其定义的是子视图的布局样式 * (不包括最后一个子视图),内部至少要包含参数 “childTo”中指定的视图ID. * @param childFrom 用于子视图显示的数据的列名列表. * @param childTo 用于显示“from”参数中指定列的子视图(来自子布局文件). * 这些视图应该都为文本视图或图像视图.视图与给定参数列的顺序是一一对应的. */ public SimpleCursorTreeAdapter(Context context, Cursor cursor, int collapsedGroupLayout, int expandedGroupLayout, String[] groupFrom, int[] groupTo, int childLayout, String[] childFrom, int[] childTo) { super(context, cursor, collapsedGroupLayout, expandedGroupLayout, childLayout); init(groupFrom, groupTo, childFrom, childTo); } /** * 构造函数 * * @param context 运行时,与 {@link SimpleCursorTreeAdapter} * 关联的 {@link ExpandableListView} 的上下文. * @param cursor 数据库游标 * @param groupLayout 定义了分组视图的资源文件的标识.布局文件至少要包含groupTo中定义的视图. * @param groupFrom 在组中显示的数据的列名. * @param groupTo 用于显示“from”参数中的列内容的分组视图(来自分组布局). * @param childLayout 布局资源文件标识ID,其定义的是子视图的布局样式 * (不包括最后一个子视图),内部至少要包含参数 “childTo”中指定的视图ID. * @param childFrom 用于子视图显示的数据的列名列表. * @param childTo 用于显示“from”参数中指定列的子视图(来自子布局文件). * 这些视图应该都为文本视图或图像视图.视图与给定参数列的顺序是一一对应的. */ public SimpleCursorTreeAdapter(Context context, Cursor cursor, int groupLayout, String[] groupFrom, int[] groupTo, int childLayout, String[] childFrom, int[] childTo) { super(context, cursor, groupLayout, childLayout); init(groupFrom, groupTo, childFrom, childTo); } private void init(String[] groupFromNames, int[] groupTo, String[] childFromNames, int[] childTo) { mGroupFromNames = groupFromNames; mGroupTo = groupTo; mChildFromNames = childFromNames; mChildTo = childTo; } /** * 返回用于绑定数据到视图的{@link ViewBinder}. * * @return ViewBinder 或者当绑定器不存在时返回空. * * @see #setViewBinder(android.widget.SimpleCursorTreeAdapter.ViewBinder) */ public ViewBinder getViewBinder() { return mViewBinder; } /** * 设置用于绑定数据到视图的绑定器. * * @param viewBinder 用于将数据绑定到视图的绑定器,若要移除既存绑定器可以设为空. * * @see #getViewBinder() */ public void setViewBinder(ViewBinder viewBinder) { mViewBinder = viewBinder; } private void bindView(View view, Context context, Cursor cursor, int[] from, int[] to) { final ViewBinder binder = mViewBinder; for (int i = 0; i < to.length; i++) { View v = view.findViewById(to[i]); if (v != null) { boolean bound = false; if (binder != null) { bound = binder.setViewValue(v, cursor, from[i]); } if (!bound) { String text = cursor.getString(from[i]); if (text == null) { text = ""; } if (v instanceof TextView) { setViewText((TextView) v, text); } else if (v instanceof ImageView) { setViewImage((ImageView) v, text); } else { throw new IllegalStateException("SimpleCursorTreeAdapter can bind values" + " only to TextView and ImageView!"); } } } } } private void initFromColumns(Cursor cursor, String[] fromColumnNames, int[] fromColumns) { for (int i = fromColumnNames.length - 1; i >= 0; i--) { fromColumns[i] = cursor.getColumnIndexOrThrow(fromColumnNames[i]); } } @Override protected void bindChildView(View view, Context context, Cursor cursor, boolean isLastChild) { if (mChildFrom == null) { mChildFrom = new int[mChildFromNames.length]; initFromColumns(cursor, mChildFromNames, mChildFrom); } bindView(view, context, cursor, mChildFrom, mChildTo); } @Override protected void bindGroupView(View view, Context context, Cursor cursor, boolean isExpanded) { if (mGroupFrom == null) { mGroupFrom = new int[mGroupFromNames.length]; initFromColumns(cursor, mGroupFromNames, mGroupFrom); } bindView(view, context, cursor, mGroupFrom, mGroupTo); } /** * 由bindView()调用,为ImageView设置图像.默认情况,字符串值作为图像URI对待. * 为需要过滤从数据库中取得的字符串的适配器重写而准备的函数. * * @param v 要设置图像的ImageView. * @param value 从游标取得的值. */ protected void setViewImage(ImageView v, String value) { try { v.setImageResource(Integer.parseInt(value)); } catch (NumberFormatException nfe) { v.setImageURI(Uri.parse(value)); } } /** * 由bindView()调用,当没有既存的 ViewBinder 或者 ViewBinder * 不能处理到文本视图的绑定时,为文本视图设置文本. * * 为需要过滤从数据库中取得的字符串的适配器重写而准备的函数. * * @param v 要设置文本的文本视图. * @param text 要设置到文本视图中的文本. */ public void setViewText(TextView v, String text) { v.setText(text); } /** * 该接口可用于 SimpleCursorTreeAdapter 的外部客户端将游标绑定到视图. * * 对于 SimpleCursorTreeAdapter 不直接支持或要改变 SimpleCursorTreeAdapter * 对游标的绑定方式时,你应该使用该类将游标的值绑定到视图. * * @see SimpleCursorTreeAdapter#setViewImage(ImageView, String) * @see SimpleCursorTreeAdapter#setViewText(TextView, String) */ public static interface ViewBinder { /** * 绑定指定位置的游标列到指定视图. * * 若该 ViewBinder 处理了绑定,该方法应该返回真.若该方法返回假, * SimpleCursorAdapter 将尝试去执行绑定操作. * * @param view 要绑定数据的视图. * @param cursor 用于取得数据的游标. * @param columnIndex 要取得数据对应的游标中的列. * * @return 若数据已绑定到视图返回真,否则返回假. */ boolean setViewValue(View view, Cursor cursor, int columnIndex); } }