Android – 使用AccountManager /手机所有者的名字和姓氏获取UserData

我想预先填充我的应用程序中的一些字段,以帮助用户在我的应用程序内订阅服务。

那么我如何获得设备所有者的名字和姓氏。 我想使用与Google帐户绑定的默认信息; 到目前为止我得到了这个:

AccountManager am = AccountManager.get(this); Account[] accounts = am.getAccounts(); for (Account account : accounts) { if (account.type.compareTo("com.google") == 0) { String possibleEmail = account.name; // how to get firstname and lastname here? } } 

如果你建议,我愿意采取其他方法 – 只要我能得到所有者的电子邮件,名字和姓氏。

在Ice Cream Sandwich中获取此信息非常简单,因为Android包含代表设备所有者的个人配置文件 – 此配置文件称为“Me”配置文件,存储在ContactsContract.Profile表中。 只要您在AndroidManifest.xml中请求READ_PROFILEREAD_CONTACTS权限,就可以从用户的配置文件中读取数据。

与您最相关的字段是Contact中的DISPLAY_NAME列,可能还有StructuredName字段 – 用户的联系人照片等内容也可用。

有一个Android代码实验室教程,提供了阅读用户配置文件的完整示例 ,代码的核心位在ListProfileTask 。 这是一个简略的片段:

 Cursor c = activity.getContentResolver().query(ContactsContract.Profile.CONTENT_URI, null, null, null, null); int count = c.getCount(); String[] columnNames = c.getColumnNames(); boolean b = c.moveToFirst(); int position = c.getPosition(); if (count == 1 && position == 0) { for (int j = 0; j < columnNames.length; j++) { String columnName = columnNames[j]; String columnValue = c.getString(c.getColumnIndex(columnName))); ... // consume the values here } } c.close(); 

不幸的是,我认为在API级别14之前没有办法获得这种数据。

这是我如何做到的(也来自api 14):

 public class MainActivity implements LoaderManager.LoaderCallbacks { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); getSupportLoaderManager().initLoader(0, null, this); } @Override public Loader onCreateLoader(int id, Bundle args) { return new CursorLoader(this, // Retrieve data rows for the device user's 'profile' contact. Uri.withAppendedPath( ContactsContract.Profile.CONTENT_URI, ContactsContract.Contacts.Data.CONTENT_DIRECTORY), ProfileQuery.PROJECTION, // Select only name. ContactsContract.Contacts.Data.MIMETYPE + "=?", new String[]{ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE}, // Show primary fields first. Note that there won't be // a primary fields if the user hasn't specified one. ContactsContract.Contacts.Data.IS_PRIMARY + " DESC"); } @Override public void onLoadFinished(Loader loader, Cursor cursor) { User user = new User(); List names = new ArrayList<>(); cursor.moveToFirst(); String mimeType; while (!cursor.isAfterLast()) { mimeType = cursor.getString(ProfileQuery.MIME_TYPE); switch (mimeType) { case ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE: String name = cursor.getString(ProfileQuery.GIVEN_NAME) + " " + cursor.getString(ProfileQuery.FAMILY_NAME); if (!TextUtils.isEmpty(name)) { names.add(name); } break; } cursor.moveToNext(); } if (!names.isEmpty()) { // do with names whatever you want } } @Override public void onLoaderReset(Loader loader) { } private interface ProfileQuery { String[] PROJECTION = { ContactsContract.CommonDataKinds.StructuredName.FAMILY_NAME, ContactsContract.CommonDataKinds.StructuredName.GIVEN_NAME, ContactsContract.Contacts.Data.MIMETYPE }; /** * Column index for the family name in the profile query results */ int FAMILY_NAME = 0; /** * Column index for the given name in the profile query results */ int GIVEN_NAME = 1; /** * Column index for the MIME type in the profile query results */ int MIME_TYPE = 2; } 

并且应该有权限: