1 /*
2  * Copyright (C) 2020 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.example.android.receivecontent;
18 
19 import android.content.ClipData;
20 import android.content.ClipDescription;
21 import android.net.Uri;
22 import android.util.Pair;
23 import android.view.ContentInfo;
24 
25 import java.util.ArrayList;
26 import java.util.List;
27 import java.util.function.Predicate;
28 
29 final class Utils {
Utils()30     private Utils() {}
31 
32     /**
33      * If you use Jetpack, use {@code androidx.core.view.ContentInfoCompat.partition()}.
34      */
partition(ContentInfo payload, Predicate<ClipData.Item> itemPredicate)35     public static Pair<ContentInfo, ContentInfo> partition(ContentInfo payload,
36             Predicate<ClipData.Item> itemPredicate) {
37         ClipData clip = payload.getClip();
38         if (clip.getItemCount() == 1) {
39             boolean matched = itemPredicate.test(clip.getItemAt(0));
40             return Pair.create(matched ? payload : null, matched ? null : payload);
41         }
42         ArrayList<ClipData.Item> acceptedItems = new ArrayList<>();
43         ArrayList<ClipData.Item> remainingItems = new ArrayList<>();
44         for (int i = 0; i < clip.getItemCount(); i++) {
45             ClipData.Item item = clip.getItemAt(i);
46             if (itemPredicate.test(item)) {
47                 acceptedItems.add(item);
48             } else {
49                 remainingItems.add(item);
50             }
51         }
52         if (acceptedItems.isEmpty()) {
53             return Pair.create(null, payload);
54         }
55         if (remainingItems.isEmpty()) {
56             return Pair.create(payload, null);
57         }
58         ContentInfo accepted = new ContentInfo.Builder(payload)
59                 .setClip(buildClipData(new ClipDescription(clip.getDescription()), acceptedItems))
60                 .build();
61         ContentInfo remaining = new ContentInfo.Builder(payload)
62                 .setClip(buildClipData(new ClipDescription(clip.getDescription()), remainingItems))
63                 .build();
64         return Pair.create(accepted, remaining);
65     }
66 
buildClipData(ClipDescription description, List<ClipData.Item> items)67     private static ClipData buildClipData(ClipDescription description,
68             List<ClipData.Item> items) {
69         ClipData clip = new ClipData(new ClipDescription(description), items.get(0));
70         for (int i = 1; i < items.size(); i++) {
71             clip.addItem(items.get(i));
72         }
73         return clip;
74     }
75 
collectUris(ClipData clip)76     public static List<Uri> collectUris(ClipData clip) {
77         List<Uri> uris = new ArrayList<>(clip.getItemCount());
78         for (int i = 0; i < clip.getItemCount(); i++) {
79             Uri uri = clip.getItemAt(i).getUri();
80             if (uri != null) {
81                 uris.add(uri);
82             }
83         }
84         return uris;
85     }
86 }
87