单击自定义联系人raw时如何设置intent bundle extra

时间:2018-02-22 05:55:57

标签: android android-intent android-syncadapter

我创建了一个联系人同步适配器来连接正在使用我的应用程序的用户(就像whatsapp,viber正在做的那样)。我将我的联系人与服务器同步以比较并获取正在使用该应用程序的用户。然后我获取这些用户的列表并在联系人中添加自定义行,如下图所示。

My sample Contact in the local phone book

单击它后会打开我的应用程序。但是我想用意图设置联系人姓名和号码(如果可能的话,也可以是contact_id)。我没有任何想法来完成这项任务。

以下是我添加新联系人的原因。

public  void addAccount(String displayName, String phone, Context context) {
    if (context == null || TextUtils.isEmpty(displayName) || TextUtils.isEmpty(phone)) return;

    ContentResolver resolver = context.getContentResolver();
    ArrayList<ContentProviderOperation> providerOperations = new ArrayList<>();

    // add the account type
    providerOperations.add(ContentProviderOperation
            .newInsert(ContactsContract.RawContacts.CONTENT_URI)
            .withValue(ContactsContract.RawContacts.ACCOUNT_NAME, "vnd.android.cursor.item/com.example.myapp")
            .withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, "com.example.myapp")
            .withValue(ContactsContract.RawContacts.AGGREGATION_MODE,
                    ContactsContract.RawContacts.AGGREGATION_MODE_DEFAULT)
            .build());

    // create a new raw contact in the table
    providerOperations.add(ContentProviderOperation
            .newInsert(ContactsContract.Data.CONTENT_URI)
            .withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0)
            .withValue(ContactsContract.Data.MIMETYPE,
                    ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)
            .withValue(ContactsContract.CommonDataKinds.StructuredName.DISPLAY_NAME, displayName)
            .build());

    // add the custom action and the mime type
    providerOperations.add(ContentProviderOperation
            .newInsert(ContactsContract.Data.CONTENT_URI)
            .withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0)
            .withValue(ContactsContract.Data.MIMETYPE, context.getString(R.string.contact_mime_type))
            .withValue(ContactsContract.Data.DATA1, phone)
            .withValue(ContactsContract.Data.DATA2, displayName)
            .withValue(ContactsContract.Data.DATA3, "Message (" + phone + ")") // the new list item shown in the contact
            .build());

    try {
        // add all the provider operations
        resolver.applyBatch(ContactsContract.AUTHORITY, providerOperations);
        Log.i(TAG, "account added for contact - '" + displayName + "'");
    } catch (Exception e) {
        Log.e(TAG, "error: " + e.getMessage());
        e.printStackTrace();
    }
}

authenticator.xml

<account-authenticator xmlns:android="http://schemas.android.com/apk/res/android"
android:accountPreferences="@xml/account_preferences"
android:accountType="com.example.myapp"
android:icon="@mipmap/ic_launcher_round"
android:label="@string/app_name"
android:smallIcon="@mipmap/ic_launcher_round" />

contacts.xml

<ContactsSource xmlns:android="http://schemas.android.com/apk/res/android">
<ContactsDataKind
    android:detailColumn="data3"
    android:detailSocialSummary="true"
    android:icon="@mipmap/ic_launcher_round"
    android:mimeType="vnd.android.cursor.item/com.example.myapp"
    android:summaryColumn="data2" />

sync_contacts.xml

<sync-adapter xmlns:android="http://schemas.android.com/apk/res/android"
android:accountType="com.example.myapp"
android:contentAuthority="com.android.contacts"
android:isAlwaysSyncable="true"
android:supportsUploading="true"
android:userVisible="true" />

清单 -

<application
    android:name=".MyApplication"
    android:allowBackup="true"
    android:icon="@mipmap/ic_launcher"
    android:label="@string/app_name"
    android:resizeableActivity="false"
    android:roundIcon="@mipmap/ic_launcher_round"
    android:supportsPictureInPicture="false"
    android:supportsRtl="true"
    android:theme="@style/AppTheme">
    <activity
        android:name=".ui.activity.SplashScreenActivity"
        android:label="@string/app_name">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
        <intent-filter tools:ignore="AppLinkUrlError">
            <action android:name="android.intent.action.VIEW" />
            <data android:mimeType="vnd.android.cursor.item/com.example.myapp" />
            <category android:name="android.intent.category.DEFAULT" />
        </intent-filter>
    </activity>

    <service
        android:name=".sync.ContactsSyncAdapterService"
        android:exported="true"
        android:process=":contacts">
        <intent-filter>
            <action android:name="android.content.SyncAdapter" />
        </intent-filter>

        <meta-data
            android:name="android.content.SyncAdapter"
            android:resource="@xml/sync_contacts" />
        <meta-data
            android:name="android.provider.CONTACTS_STRUCTURE"
            android:resource="@xml/contacts" />
    </service>

    <service
        android:name=".sync.AuthenticatorService"
        android:exported="true"
        android:process=":auth">
        <intent-filter>
            <action android:name="android.accounts.AccountAuthenticator" />
        </intent-filter>

        <meta-data
            android:name="android.accounts.AccountAuthenticator"
            android:resource="@xml/authenticator" />
    </service>

</application>

最后,当我在SplashScreenActivity - onCreate方法中打印意图操作时,它会在联系人操作点击启动时显示android.intent.action.VIEW,并在正常应用启动时显示android.intent.action.MAIN

1 个答案:

答案 0 :(得分:0)

终于找到了解决方案。我们可以从Viewing Intent获取联系人的内容URI。 我们可以从内容URI访问联系人。

private void getContactFromUri() {
    String dataString = getIntent().getDataString();
    Uri uri = Uri.parse(dataString);
    String[] projection = {ContactsContract.CommonDataKinds.Phone.NUMBER, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME};

    Cursor cursor = getContentResolver().query(uri, projection,
            null, null, null);
    if (cursor != null) {
        if (cursor.moveToFirst()) {
            String name = cursor.getString(
                    cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
            String number = cursor.getString(
                    cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
            cursor.close();
        }
        cursor.close();
    }
}