您的位置:首页 > 其它

基于PinnedSectionListView实现联系人通讯录并且点击打电话

2015-12-24 10:37 232 查看




<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
>

<com.zzw.contacts.PinnedSectionListView
android:id="@+id/listView"
android:layout_width="match_parent"
android:layout_height="match_parent" />

</RelativeLayout>

activity_main.xml


权限:

<!-- 写权限 -->
<uses-permission android:name="android.permission.WRITE_CONTACTS" />
<!-- 读权限 -->
<uses-permission android:name="android.permission.READ_CONTACTS" />
<!-- 打电话权限 -->
<uses-permission android:name="android.permission.CALL_PHONE" />


package com.zzw.contacts;

import java.util.ArrayList;

import com.zzw.contacts.PinnedSectionListView.PinnedSectionListAdapter;

import android.app.Activity;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.database.Cursor;
import android.graphics.Color;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.TextView;

public class MainActivity extends Activity {

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

ArrayList<Contact> contacts = new ArrayList<Contact>();
readContacts(contacts);

final ArrayList<Item> items = new ArrayList<Item>();

// 从字母A开始到Z。26个字母,遍历联系人中的首字符是否相等。
// 相等则归入一组。
int A = (int) 'A';
for (int i = 0; i < 26; i++) {
int letter = A + i;
char c = (char) letter;

Item group = new Item();
group.type = Item.GROUP;
group.text = c + "";
items.add(group);

for (int j = 0; j < contacts.size(); j++) {
Contact contact = contacts.get(j);
String s = contact.firstLetterOfName();
if (s.equals(group.text)) {
Item child = new Item();
child.type = Item.CHILD;
child.text = contact.name + "  " + contact.getPhoneNumbers();
child.contact = contact;
items.add(child);
}
}
}

PinnedSectionListView listView = (PinnedSectionListView) findViewById(R.id.listView);

ArrayAdapter<Item> adapter = new MyAdapter(this, -1, items);
listView.setAdapter(adapter);

listView.setOnItemClickListener(new OnItemClickListener() {

@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Item item = items.get(position);

if (item.type == Item.CHILD) {
Contact contact = item.contact;
// 简单演示期间,我们只选择第一个电话(不管有几个电话)。
String number = contact.phoneNumbers.get(0);
if (!number.equals("")) {
// 拨打电话
Intent intent = new Intent(Intent.ACTION_CALL, Uri.parse("tel:" + number));
startActivity(intent);
}
}
}
});

}

private class MyAdapter extends ArrayAdapter<Item>implements PinnedSectionListAdapter {

private LayoutInflater inflater;
private ArrayList<Item> items;

public MyAdapter(Context context, int resource, ArrayList<Item> items) {
super(context, resource, items);
this.items = items;
inflater = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}

@Override
public int getCount() {
return items.size();
}

@Override
public int getItemViewType(int position) {

return items.get(position).type;
}

@Override
public int getViewTypeCount() {

return 2;
}

@Override
public Item getItem(int position) {
return items.get(position);
}

@Override
public View getView(int position, View convertView, ViewGroup parent) {

String text = getItem(position).text;

switch (getItemViewType(position)) {
case Item.GROUP:

if (convertView == null) {
convertView = inflater.inflate(android.R.layout.simple_list_item_1, null);
}

TextView text1 = (TextView) convertView.findViewById(android.R.id.text1);

// 首字符,分组的依据
text1.setText(text);
text1.setBackgroundColor(Color.GRAY);

break;

case Item.CHILD:
if (convertView == null) {
convertView = inflater.inflate(android.R.layout.simple_list_item_2, null);
}

TextView text2 = (TextView) convertView.findViewById(android.R.id.text2);
text2.setText(text);

break;
}
return convertView;
}

// 假设此方法返回皆为false。那么PinnedSectionListView将退化成为一个基础的ListView.
// 只不过退化后的ListView只是一个拥有两个View Type的ListView。
// 从某种角度上讲,此方法对于PinnedSectionListView至关重要,因为返回值true或false,
// 将直接导致PinnedSectionListView是一个PinnedSectionListView,还是一个普通的ListView。
@Override
public boolean isItemViewTypePinned(int viewType) {
boolean type = false;
switch (viewType) {
case Item.GROUP:
type = true;
break;

case Item.CHILD:
type = false;
break;

default:
type = false;
break;
}
return type;
}

}

// 读取设备联系人的一般方法。大致流程就是这样,模板化的操作代码。
private void readContacts(ArrayList<Contact> contacts) {
Uri uri = Uri.parse("content://com.android.contacts/contacts");
ContentResolver resolver = this.getContentResolver();

// 在这里我们给query传递进去一个SORT_KEY_PRIMARY
// 告诉ContentResolver获得的结果按照联系人名字的首字母有序排序
Cursor cursor = resolver.query(uri, null, null, null,
android.provider.ContactsContract.Contacts.SORT_KEY_PRIMARY);

while (cursor.moveToNext()) {
// 联系人id
String id = cursor.getString(cursor.getColumnIndex(android.provider.ContactsContract.Contacts._ID));
// Sort key,读取的联系人按照姓名从 A->Z 的排序分组
String sork_key_primary = cursor
.getString(cursor.getColumnIndex(android.provider.ContactsContract.Contacts.SORT_KEY_PRIMARY));
// 获取联系人姓名
String name = cursor
.getString(cursor.getColumnIndex(android.provider.ContactsContract.Contacts.DISPLAY_NAME));

Contact mContact = new Contact();
mContact.id = id;
mContact.sort_key_primay = sork_key_primary;
mContact.name = name;

// 获取联系人的手机号码
Cursor phone = resolver.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + "=" + id, null, null);
// 取得电话号码(可能存在多个号码)
// 因为在同一个名字下,用户可能存有一个以上号码
// 遍历
ArrayList<String> phoneNumbers = new ArrayList<String>();
while (phone.moveToNext()) {
int phoneFieldColumnIndex = phone.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER);
String phoneNumber = phone.getString(phoneFieldColumnIndex);
phoneNumbers.add(phoneNumber);
}

mContact.phoneNumbers = phoneNumbers;
contacts.add(mContact);
}
}

// 用于承载数据块的类。
// 字段分为类型(type)和值(text)。
private class Item {
public static final int GROUP = 0;
public static final int CHILD = 1;

public int type;
public String text;

public Contact contact = null;
}

// 用于装载从联系人数据库中读取到的数据。
// 结构化数据,便于数据操作和访问。
private class Contact {
public String id;
public String name;
public String sort_key_primay;
public ArrayList<String> phoneNumbers;

// 获得一个联系人名字的首字母。
// 比如一个人的名字叫做“安卓”,那么这个人的首字母是:A
public String firstLetterOfName() {
String s = sort_key_primay.charAt(0) + "";

return s.toUpperCase();
}

public String getPhoneNumbers() {
String phones = "";
for (int i = 0; i < phoneNumbers.size(); i++) {
phones += ":     " + phoneNumbers.get(i);
}
return phones;
}
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: