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.inlinefillservice;
18 
19 import static com.example.android.inlinefillservice.InlineFillService.TAG;
20 
21 import android.content.Context;
22 import android.content.IntentSender;
23 import android.service.autofill.Dataset;
24 import android.service.autofill.InlinePresentation;
25 import android.util.Log;
26 import android.view.autofill.AutofillId;
27 import android.view.autofill.AutofillValue;
28 import android.view.inputmethod.InlineSuggestionsRequest;
29 import android.widget.RemoteViews;
30 
31 import androidx.annotation.NonNull;
32 
33 import java.util.Map;
34 import java.util.Optional;
35 
36 class ResponseHelper {
37 
newUnlockedDataset(@onNull Context context, @NonNull Map<String, AutofillId> fields, @NonNull String packageName, int index, @NonNull Optional<InlineSuggestionsRequest> inlineRequest)38     static Dataset newUnlockedDataset(@NonNull Context context,
39             @NonNull Map<String, AutofillId> fields, @NonNull String packageName, int index,
40             @NonNull Optional<InlineSuggestionsRequest> inlineRequest) {
41 
42         Dataset.Builder dataset = new Dataset.Builder();
43         for (Map.Entry<String, AutofillId> field : fields.entrySet()) {
44             final String hint = field.getKey();
45             final AutofillId id = field.getValue();
46             final String value = hint + (index + 1);
47 
48             // We're simple - our dataset values are hardcoded as "hintN" (for example,
49             // "username1", "username2") and they're displayed as such, except if they're a
50             // password
51             Log.d(TAG, "hint: " + hint);
52             final String displayValue = hint.contains("password") ? "password for #" + (index + 1)
53                     : value;
54             final RemoteViews presentation = newDatasetPresentation(packageName, displayValue);
55 
56             // Add Inline Suggestion required info.
57             if (inlineRequest.isPresent()) {
58                 Log.d(TAG, "Found InlineSuggestionsRequest in FillRequest: " + inlineRequest);
59                 final InlinePresentation inlinePresentation =
60                         InlineRequestHelper.createInlineDataset(context, inlineRequest.get(),
61                                 displayValue, index);
62                 dataset.setValue(id, AutofillValue.forText(value), presentation,
63                         inlinePresentation);
64             } else {
65                 dataset.setValue(id, AutofillValue.forText(value), presentation);
66             }
67         }
68 
69         return dataset.build();
70     }
71 
newLockedDataset(@onNull Context context, @NonNull Map<String, AutofillId> fields, @NonNull String packageName, int index, @NonNull Optional<InlineSuggestionsRequest> inlineRequest)72     static Dataset newLockedDataset(@NonNull Context context,
73             @NonNull Map<String, AutofillId> fields, @NonNull String packageName, int index,
74             @NonNull Optional<InlineSuggestionsRequest> inlineRequest) {
75         Dataset unlockedDataset = ResponseHelper.newUnlockedDataset(context, fields,
76                 packageName, index, inlineRequest);
77 
78         Dataset.Builder lockedDataset = new Dataset.Builder();
79         for (Map.Entry<String, AutofillId> field : fields.entrySet()) {
80             String hint = field.getKey();
81             AutofillId id = field.getValue();
82             String value = (index + 1) + "-" + hint;
83             String displayValue = "Tap to auth " + value;
84             IntentSender authentication =
85                     AuthActivity.newIntentSenderForDataset(context, unlockedDataset);
86             RemoteViews presentation = newDatasetPresentation(packageName, displayValue);
87             if (inlineRequest.isPresent()) {
88                 final InlinePresentation inlinePresentation =
89                         InlineRequestHelper.createInlineDataset(context, inlineRequest.get(),
90                         displayValue, index);
91                 lockedDataset.setValue(id, null, presentation, inlinePresentation)
92                         .setAuthentication(authentication);
93             } else {
94                 lockedDataset.setValue(id, null, presentation)
95                         .setAuthentication(authentication);
96             }
97         }
98         return lockedDataset.build();
99     }
100 
101     /**
102      * Helper method to create a dataset presentation with the givean text.
103      */
104     @NonNull
newDatasetPresentation(@onNull String packageName, @NonNull CharSequence text)105     static RemoteViews newDatasetPresentation(@NonNull String packageName,
106             @NonNull CharSequence text) {
107         RemoteViews presentation =
108                 new RemoteViews(packageName, R.layout.list_item);
109         presentation.setTextViewText(R.id.text, text);
110         return presentation;
111     }
112 }
113