1f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki/*
2f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * Copyright (C) 2017 The Android Open Source Project
3f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki *
4f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * Licensed under the Apache License, Version 2.0 (the "License");
5f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * you may not use this file except in compliance with the License.
6f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * You may obtain a copy of the License at
7f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki *
8f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki *      http://www.apache.org/licenses/LICENSE-2.0
9f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki *
10f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * Unless required by applicable law or agreed to in writing, software
11f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * distributed under the License is distributed on an "AS IS" BASIS,
12f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * See the License for the specific language governing permissions and
14f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * limitations under the License.
15f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki */
16f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
17f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokipackage android.view.textclassifier;
18f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
19f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.annotation.FloatRange;
202f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Tokiimport android.annotation.IntDef;
21f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.annotation.IntRange;
22f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.annotation.NonNull;
23f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.annotation.Nullable;
2420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althausimport android.app.PendingIntent;
2520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althausimport android.app.RemoteAction;
26f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.content.Context;
27f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.content.Intent;
282f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Tokiimport android.content.pm.PackageManager;
292f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Tokiimport android.content.pm.ResolveInfo;
30ef7cb2c0fc88513f065b8b37847dd6872ce53483Abodunrinwa Tokiimport android.content.res.Resources;
31ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Tokiimport android.graphics.BitmapFactory;
32ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Tokiimport android.graphics.drawable.AdaptiveIconDrawable;
330d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althausimport android.graphics.drawable.BitmapDrawable;
34f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.graphics.drawable.Drawable;
35ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Tokiimport android.graphics.drawable.Icon;
362b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Tokiimport android.os.LocaleList;
370d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althausimport android.os.Parcel;
380d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althausimport android.os.Parcelable;
39bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althausimport android.util.ArrayMap;
40f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.view.View.OnClickListener;
41f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport android.view.textclassifier.TextClassifier.EntityType;
42080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Tokiimport android.view.textclassifier.TextClassifier.Utils;
43f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
44f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport com.android.internal.util.Preconditions;
45f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
462f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Tokiimport java.lang.annotation.Retention;
472f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Tokiimport java.lang.annotation.RetentionPolicy;
48a1652cfcce547183a426cc710691c740b2e46aa7Jan Althausimport java.time.ZonedDateTime;
4992d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althausimport java.util.ArrayList;
5020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althausimport java.util.Collections;
51f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Tokiimport java.util.List;
524d232d6243af42e2784664f6fab040e853f05223Abodunrinwa Tokiimport java.util.Locale;
53bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althausimport java.util.Map;
54f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
55f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki/**
56f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki * Information for generating a widget to handle classified text.
5733ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
5833ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * <p>A TextClassification object contains icons, labels, onClickListeners and intents that may
59ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki * be used to build a widget that can be used to act on classified text. There is the concept of a
60ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki * <i>primary action</i> and other <i>secondary actions</i>.
6133ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
6233ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * <p>e.g. building a view that, when clicked, shares the classified text with the preferred app:
6333ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
6433ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * <pre>{@code
6533ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   // Called preferably outside the UiThread.
664d232d6243af42e2784664f6fab040e853f05223Abodunrinwa Toki *   TextClassification classification = textClassifier.classifyText(allText, 10, 25);
6733ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
6833ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   // Called on the UiThread.
6933ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   Button button = new Button(context);
7033ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   button.setCompoundDrawablesWithIntrinsicBounds(classification.getIcon(), null, null, null);
7133ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   button.setText(classification.getLabel());
72ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki *   button.setOnClickListener(v -> classification.getActions().get(0).getActionIntent().send());
7333ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * }</pre>
7433ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
7533ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * <p>e.g. starting an action mode with menu items that can handle the classified text:
7633ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
7733ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * <pre>{@code
7833ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   // Called preferably outside the UiThread.
794d232d6243af42e2784664f6fab040e853f05223Abodunrinwa Toki *   final TextClassification classification = textClassifier.classifyText(allText, 10, 25);
8033ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
8133ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   // Called on the UiThread.
8233ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   view.startActionMode(new ActionMode.Callback() {
8333ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
8433ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *       public boolean onCreateActionMode(ActionMode mode, Menu menu) {
8520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus *           for (int i = 0; i < classification.getActions().size(); ++i) {
8620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus *              RemoteAction action = classification.getActions().get(i);
8720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus *              menu.add(Menu.NONE, i, 20, action.getTitle())
8820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus *                 .setIcon(action.getIcon());
8933ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *           }
9033ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *           return true;
9133ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *       }
9233ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
9333ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *       public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
9420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus *           classification.getActions().get(item.getItemId()).getActionIntent().send();
9533ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *           return true;
9633ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *       }
9733ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *
9833ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *       ...
9933ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki *   });
10033ff200cbf5595f931ec38422cc0d4351990b762Abodunrinwa Toki * }</pre>
101f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki */
102d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Tokipublic final class TextClassification implements Parcelable {
103f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
104f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
105f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * @hide
106f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
107e0b57893c68a685d287664df28467694a39e4432Abodunrinwa Toki    static final TextClassification EMPTY = new TextClassification.Builder().build();
108f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
10920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    private static final String LOG_TAG = "TextClassification";
1100d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus    // TODO(toki): investigate a way to derive this based on device properties.
11120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    private static final int MAX_LEGACY_ICON_SIZE = 192;
1120d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
1132f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    @Retention(RetentionPolicy.SOURCE)
1142f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    @IntDef(value = {IntentType.UNSUPPORTED, IntentType.ACTIVITY, IntentType.SERVICE})
1152f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    private @interface IntentType {
1162f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        int UNSUPPORTED = -1;
1172f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        int ACTIVITY = 0;
1182f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        int SERVICE = 1;
1192f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    }
1202f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki
121f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @NonNull private final String mText;
12220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Nullable private final Drawable mLegacyIcon;
12320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Nullable private final String mLegacyLabel;
12420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Nullable private final Intent mLegacyIntent;
12520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Nullable private final OnClickListener mLegacyOnClickListener;
12620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @NonNull private final List<RemoteAction> mActions;
1270d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus    @NonNull private final EntityConfidence mEntityConfidence;
128080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki    @Nullable private final String mId;
129f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
130e0b57893c68a685d287664df28467694a39e4432Abodunrinwa Toki    private TextClassification(
131d44286f94240f79b26703cf1dcff94893135c93cAbodunrinwa Toki            @Nullable String text,
13220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            @Nullable Drawable legacyIcon,
13320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            @Nullable String legacyLabel,
13420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            @Nullable Intent legacyIntent,
13520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            @Nullable OnClickListener legacyOnClickListener,
13620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            @NonNull List<RemoteAction> actions,
137bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althaus            @NonNull Map<String, Float> entityConfidence,
138080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            @Nullable String id) {
139f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        mText = text;
14020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        mLegacyIcon = legacyIcon;
14120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        mLegacyLabel = legacyLabel;
14220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        mLegacyIntent = legacyIntent;
14320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        mLegacyOnClickListener = legacyOnClickListener;
14420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        mActions = Collections.unmodifiableList(actions);
1450d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        mEntityConfidence = new EntityConfidence(entityConfidence);
146080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        mId = id;
147f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
148f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
149f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
150f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * Gets the classified text.
151f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
152d44286f94240f79b26703cf1dcff94893135c93cAbodunrinwa Toki    @Nullable
153f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public String getText() {
154f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        return mText;
155f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
156f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
157f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
158f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * Returns the number of entities found in the classified text.
159f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
160f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @IntRange(from = 0)
161f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public int getEntityCount() {
162bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althaus        return mEntityConfidence.getEntities().size();
163f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
164f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
165f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
166f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * Returns the entity at the specified index. Entities are ordered from high confidence
167f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * to low confidence.
168f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     *
169f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * @throws IndexOutOfBoundsException if the specified index is out of range.
170f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * @see #getEntityCount() for the number of entities available.
171f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
172f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @NonNull
173f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public @EntityType String getEntity(int index) {
174bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althaus        return mEntityConfidence.getEntities().get(index);
175f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
176f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
177f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
178f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * Returns the confidence score for the specified entity. The value ranges from
179f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * 0 (low confidence) to 1 (high confidence). 0 indicates that the entity was not found for the
180f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * classified text.
181f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
182f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @FloatRange(from = 0.0, to = 1.0)
183f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public float getConfidenceScore(@EntityType String entity) {
184f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        return mEntityConfidence.getConfidenceScore(entity);
185f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
186f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
187f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
18820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * Returns a list of actions that may be performed on the text. The list is ordered based on
18920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * the likelihood that a user will use the action, with the most likely action appearing first.
19092d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus     */
19120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    public List<RemoteAction> getActions() {
19220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return mActions;
19392d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus    }
19492d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus
19592d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus    /**
19620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * Returns an icon that may be rendered on a widget used to act on the classified text.
197ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *
198ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * <p><strong>NOTE: </strong>This field is not parcelable and only represents the icon of the
199ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * first {@link RemoteAction} (if one exists) when this object is read from a parcel.
200ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     *
20120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * @deprecated Use {@link #getActions()} instead.
202f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
20320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Deprecated
204f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @Nullable
205f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public Drawable getIcon() {
20620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return mLegacyIcon;
20792d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus    }
20892d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus
20992d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus    /**
21020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * Returns a label that may be rendered on a widget used to act on the classified text.
211ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *
212ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * <p><strong>NOTE: </strong>This field is not parcelable and only represents the label of the
213ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * first {@link RemoteAction} (if one exists) when this object is read from a parcel.
214ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     *
21520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * @deprecated Use {@link #getActions()} instead.
216f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
21720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Deprecated
218f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @Nullable
219f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public CharSequence getLabel() {
22020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return mLegacyLabel;
22192d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus    }
22292d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus
22392d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus    /**
22420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * Returns an intent that may be fired to act on the classified text.
225ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *
226ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * <p><strong>NOTE: </strong>This field is not parcelled and will always return null when this
227ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * object is read from a parcel.
228ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     *
22920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * @deprecated Use {@link #getActions()} instead.
230f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
23120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    @Deprecated
232f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @Nullable
233f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public Intent getIntent() {
23420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return mLegacyIntent;
235f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
236f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
237f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
238ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * Returns the OnClickListener that may be triggered to act on the classified text.
239ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     *
240ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * <p><strong>NOTE: </strong>This field is not parcelable and only represents the first
241ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki     * {@link RemoteAction} (if one exists) when this object is read from a parcel.
24220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     *
24320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * @deprecated Use {@link #getActions()} instead.
244f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
245f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @Nullable
246f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public OnClickListener getOnClickListener() {
24720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return mLegacyOnClickListener;
248f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
249f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
25054486c16bac3b31dc04074d2377fe8c63a2e4a0fAbodunrinwa Toki    /**
251080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki     * Returns the id, if one exists, for this object.
252692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki     */
253080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki    @Nullable
254080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki    public String getId() {
255080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        return mId;
256692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki    }
257692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki
258f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    @Override
259f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public String toString() {
26020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return String.format(Locale.US,
261080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                "TextClassification {text=%s, entities=%s, actions=%s, id=%s}",
262080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                mText, mEntityConfidence, mActions, mId);
263f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
264f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
265f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
26620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * Creates an OnClickListener that triggers the specified PendingIntent.
26720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     *
26820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * @hide
26920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     */
27020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    public static OnClickListener createIntentOnClickListener(@NonNull final PendingIntent intent) {
27120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        Preconditions.checkNotNull(intent);
27220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        return v -> {
27320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            try {
27420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus                intent.send();
27520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            } catch (PendingIntent.CanceledException e) {
276080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                Log.e(LOG_TAG, "Error sending PendingIntent", e);
27720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            }
27820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        };
27920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    }
28020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus
28120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    /**
28220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     * Creates a PendingIntent for the specified intent.
2832f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki     * Returns null if the intent is not supported for the specified context.
284f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     *
285f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * @throws IllegalArgumentException if context or intent is null
286f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     * @hide
287f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
2882f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    @Nullable
28920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus    public static PendingIntent createPendingIntent(
290904a931cfc5f2ffd6fd0c0fb03718abca37b5ee5Abodunrinwa Toki            @NonNull final Context context, @NonNull final Intent intent, int requestCode) {
291aec5981b88b7b223363561e0ceee0be2750a0458Abodunrinwa Toki        final int flags = PendingIntent.FLAG_UPDATE_CURRENT;
2922f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        switch (getIntentType(intent, context)) {
2932f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            case IntentType.ACTIVITY:
294aec5981b88b7b223363561e0ceee0be2750a0458Abodunrinwa Toki                return PendingIntent.getActivity(context, requestCode, intent, flags);
2952f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            case IntentType.SERVICE:
296aec5981b88b7b223363561e0ceee0be2750a0458Abodunrinwa Toki                return PendingIntent.getService(context, requestCode, intent, flags);
2972f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            default:
2982f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki                return null;
2992f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        }
3002f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    }
3012f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki
3022f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    @IntentType
3032f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    private static int getIntentType(@NonNull Intent intent, @NonNull Context context) {
304f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        Preconditions.checkArgument(context != null);
305f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        Preconditions.checkArgument(intent != null);
3062f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki
3072f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        final ResolveInfo activityRI = context.getPackageManager().resolveActivity(intent, 0);
3082f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        if (activityRI != null) {
3092f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            if (context.getPackageName().equals(activityRI.activityInfo.packageName)) {
3102f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki                return IntentType.ACTIVITY;
3112f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            }
3122f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            final boolean exported = activityRI.activityInfo.exported;
3132f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            if (exported && hasPermission(context, activityRI.activityInfo.permission)) {
3142f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki                return IntentType.ACTIVITY;
3152f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            }
3162f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        }
3172f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki
3182f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        final ResolveInfo serviceRI = context.getPackageManager().resolveService(intent, 0);
3192f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        if (serviceRI != null) {
3202f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            if (context.getPackageName().equals(serviceRI.serviceInfo.packageName)) {
3212f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki                return IntentType.SERVICE;
3222f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            }
3232f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            final boolean exported = serviceRI.serviceInfo.exported;
3242f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            if (exported && hasPermission(context, serviceRI.serviceInfo.permission)) {
3252f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki                return IntentType.SERVICE;
3262f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki            }
3272f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        }
3282f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki
3292f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        return IntentType.UNSUPPORTED;
3302f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    }
3312f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki
3322f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki    private static boolean hasPermission(@NonNull Context context, @NonNull String permission) {
3332f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki        return permission == null
3342f19b92c756c539e16bbd730f117acfcdf98b4ceAbodunrinwa Toki                || context.checkSelfPermission(permission) == PackageManager.PERMISSION_GRANTED;
335f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
336f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
337f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    /**
338e0b57893c68a685d287664df28467694a39e4432Abodunrinwa Toki     * Builder for building {@link TextClassification} objects.
339ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *
340ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     * <p>e.g.
341ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *
342ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     * <pre>{@code
343ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *   TextClassification classification = new TextClassification.Builder()
344ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *          .setText(classifiedText)
345ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *          .setEntityType(TextClassifier.TYPE_EMAIL, 0.9)
346ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *          .setEntityType(TextClassifier.TYPE_OTHER, 0.1)
34720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     *          .addAction(remoteAction1)
34820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus     *          .addAction(remoteAction2)
349ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     *          .build();
350ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki     * }</pre>
351f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki     */
352f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    public static final class Builder {
353f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
35420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        @NonNull private List<RemoteAction> mActions = new ArrayList<>();
355bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althaus        @NonNull private final Map<String, Float> mEntityConfidence = new ArrayMap<>();
35613a89c94031cf93fa60478803f2ace9127a5f7f9Jan Althaus        @Nullable private String mText;
35713a89c94031cf93fa60478803f2ace9127a5f7f9Jan Althaus        @Nullable private Drawable mLegacyIcon;
35813a89c94031cf93fa60478803f2ace9127a5f7f9Jan Althaus        @Nullable private String mLegacyLabel;
35913a89c94031cf93fa60478803f2ace9127a5f7f9Jan Althaus        @Nullable private Intent mLegacyIntent;
36013a89c94031cf93fa60478803f2ace9127a5f7f9Jan Althaus        @Nullable private OnClickListener mLegacyOnClickListener;
361080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @Nullable private String mId;
362f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
363f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        /**
364f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         * Sets the classified text.
365f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         */
366080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
367d44286f94240f79b26703cf1dcff94893135c93cAbodunrinwa Toki        public Builder setText(@Nullable String text) {
368d44286f94240f79b26703cf1dcff94893135c93cAbodunrinwa Toki            mText = text;
369f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki            return this;
370f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        }
371f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
372f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        /**
373f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         * Sets an entity type for the classification result and assigns a confidence score.
374ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * If a confidence score had already been set for the specified entity type, this will
375ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * override that score.
376f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         *
377f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         * @param confidenceScore a value from 0 (low confidence) to 1 (high confidence).
378f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         *      0 implies the entity does not exist for the classified text.
379f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         *      Values greater than 1 are clamped to 1.
380f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         */
381080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
382f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        public Builder setEntityType(
383f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki                @NonNull @EntityType String type,
384d44286f94240f79b26703cf1dcff94893135c93cAbodunrinwa Toki                @FloatRange(from = 0.0, to = 1.0) float confidenceScore) {
385bbe43dfd97c01364e46df452be4c99536d64e4fbJan Althaus            mEntityConfidence.put(type, confidenceScore);
386f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki            return this;
387f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        }
388f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
389f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        /**
39020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * Adds an action that may be performed on the classified text. Actions should be added in
39120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * order of likelihood that the user will use them, with the most likely action being added
39220d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * first.
39392d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus         */
394080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
39520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        public Builder addAction(@NonNull RemoteAction action) {
39620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            Preconditions.checkArgument(action != null);
39720d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            mActions.add(action);
39892d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus            return this;
39992d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus        }
40092d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus
40192d76838f8122917c51a2ea7f04fa04d7c9275a9Jan Althaus        /**
402ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * Sets the icon for the <i>primary</i> action that may be rendered on a widget used to act
403ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * on the classified text.
404ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         *
405ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * <p><strong>NOTE: </strong>This field is not parcelled. If read from a parcel, the
406ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * returned icon represents the icon of the first {@link RemoteAction} (if one exists).
407ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         *
40820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * @deprecated Use {@link #addAction(RemoteAction)} instead.
409f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         */
41020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        @Deprecated
411080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
412f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        public Builder setIcon(@Nullable Drawable icon) {
41320d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            mLegacyIcon = icon;
414f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki            return this;
415f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        }
416f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
417f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        /**
418ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * Sets the label for the <i>primary</i> action that may be rendered on a widget used to
419ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * act on the classified text.
420ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         *
421ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * <p><strong>NOTE: </strong>This field is not parcelled. If read from a parcel, the
422ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * returned label represents the label of the first {@link RemoteAction} (if one exists).
423ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         *
42420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * @deprecated Use {@link #addAction(RemoteAction)} instead.
425f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         */
42620d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        @Deprecated
427080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
428f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        public Builder setLabel(@Nullable String label) {
42920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            mLegacyLabel = label;
430f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki            return this;
431f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        }
432f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
433f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        /**
434ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * Sets the intent for the <i>primary</i> action that may be fired to act on the classified
435ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * text.
436ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         *
437ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * <p><strong>NOTE: </strong>This field is not parcelled.
438ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         *
43920d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * @deprecated Use {@link #addAction(RemoteAction)} instead.
440f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         */
44120d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        @Deprecated
442080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
443f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        public Builder setIntent(@Nullable Intent intent) {
44420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            mLegacyIntent = intent;
445f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki            return this;
446f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        }
447f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki
448f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        /**
449ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki         * Sets the OnClickListener for the <i>primary</i> action that may be triggered to act on
450ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * the classified text.
451ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         *
452ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * <p><strong>NOTE: </strong>This field is not parcelable. If read from a parcel, the
453ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki         * returned OnClickListener represents the first {@link RemoteAction} (if one exists).
45420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         *
45520d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus         * @deprecated Use {@link #addAction(RemoteAction)} instead.
45654486c16bac3b31dc04074d2377fe8c63a2e4a0fAbodunrinwa Toki         */
457080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @Deprecated
458080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
459ba3856266cff7e6865eb23ec0828b2a0aee2c79fAbodunrinwa Toki        public Builder setOnClickListener(@Nullable OnClickListener onClickListener) {
46020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            mLegacyOnClickListener = onClickListener;
46154486c16bac3b31dc04074d2377fe8c63a2e4a0fAbodunrinwa Toki            return this;
46254486c16bac3b31dc04074d2377fe8c63a2e4a0fAbodunrinwa Toki        }
46354486c16bac3b31dc04074d2377fe8c63a2e4a0fAbodunrinwa Toki
46454486c16bac3b31dc04074d2377fe8c63a2e4a0fAbodunrinwa Toki        /**
465080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         * Sets an id for the TextClassification object.
466692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki         */
467080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
468080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        public Builder setId(@Nullable String id) {
469080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mId = id;
470692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki            return this;
471692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki        }
472692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki
473692b196cc12f6852b0bb9009c882a69b67dda4d8Abodunrinwa Toki        /**
474e0b57893c68a685d287664df28467694a39e4432Abodunrinwa Toki         * Builds and returns a {@link TextClassification} object.
475f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki         */
476080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
477e0b57893c68a685d287664df28467694a39e4432Abodunrinwa Toki        public TextClassification build() {
47820d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus            return new TextClassification(mText, mLegacyIcon, mLegacyLabel, mLegacyIntent,
479080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                    mLegacyOnClickListener, mActions, mEntityConfidence, mId);
480f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki        }
481f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki    }
4822b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki
4832b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki    /**
484080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki     * A request object for generating TextClassification.
4852b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki     */
486080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki    public static final class Request implements Parcelable {
487080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
488080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        private final CharSequence mText;
489080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        private final int mStartIndex;
490080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        private final int mEndIndex;
491080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @Nullable private final LocaleList mDefaultLocales;
492080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @Nullable private final ZonedDateTime mReferenceTime;
493080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
494080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        private Request(
495080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                CharSequence text,
496080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                int startIndex,
497080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                int endIndex,
498080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                LocaleList defaultLocales,
499080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                ZonedDateTime referenceTime) {
500080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mText = text;
501080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mStartIndex = startIndex;
502080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mEndIndex = endIndex;
503080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mDefaultLocales = defaultLocales;
504080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mReferenceTime = referenceTime;
505080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        }
5062b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki
507080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        /**
508080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         * Returns the text providing context for the text to classify (which is specified
509080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         *      by the sub sequence starting at startIndex and ending at endIndex)
510080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         */
511080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @NonNull
512080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        public CharSequence getText() {
513080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            return mText;
514080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        }
5152b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki
5162b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki        /**
517080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         * Returns start index of the text to classify.
5182b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki         */
519080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @IntRange(from = 0)
520080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        public int getStartIndex() {
521080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            return mStartIndex;
5222b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki        }
5232b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki
5242b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki        /**
525080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         * Returns end index of the text to classify.
526705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus         */
527080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        @IntRange(from = 0)
528080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        public int getEndIndex() {
529080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            return mEndIndex;
530705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus        }
531705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus
532705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus        /**
5332b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki         * @return ordered list of locale preferences that can be used to disambiguate
5342b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki         *      the provided text.
5352b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki         */
5362b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki        @Nullable
5372b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki        public LocaleList getDefaultLocales() {
5382b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki            return mDefaultLocales;
5392b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki        }
5400d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
541705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus        /**
542705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus         * @return reference time based on which relative dates (e.g. "tomorrow") should be
543705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus         *      interpreted.
544705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus         */
545705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus        @Nullable
546a1652cfcce547183a426cc710691c740b2e46aa7Jan Althaus        public ZonedDateTime getReferenceTime() {
547705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus            return mReferenceTime;
548705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus        }
549705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus
550080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        /**
551080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         * A builder for building TextClassification requests.
552080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki         */
553080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        public static final class Builder {
554080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
555080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            private final CharSequence mText;
556080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            private final int mStartIndex;
557080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            private final int mEndIndex;
558080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
559080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            @Nullable private LocaleList mDefaultLocales;
560080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            @Nullable private ZonedDateTime mReferenceTime;
561080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
562080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            /**
563080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @param text text providing context for the text to classify (which is specified
564080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *      by the sub sequence starting at startIndex and ending at endIndex)
565080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @param startIndex start index of the text to classify
566080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @param endIndex end index of the text to classify
567080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             */
568080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            public Builder(
569080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                    @NonNull CharSequence text,
570080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                    @IntRange(from = 0) int startIndex,
571080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                    @IntRange(from = 0) int endIndex) {
572080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                Utils.checkArgument(text, startIndex, endIndex);
573080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                mText = text;
574080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                mStartIndex = startIndex;
575080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                mEndIndex = endIndex;
576080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            }
577080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
578080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            /**
579080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @param defaultLocales ordered list of locale preferences that may be used to
580080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *      disambiguate the provided text. If no locale preferences exist, set this to null
581080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *      or an empty locale list.
582080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *
583080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @return this builder
584080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             */
585080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            @NonNull
586080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            public Builder setDefaultLocales(@Nullable LocaleList defaultLocales) {
587080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                mDefaultLocales = defaultLocales;
588080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                return this;
589080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            }
590080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
591080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            /**
592080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @param referenceTime reference time based on which relative dates (e.g. "tomorrow"
593080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *      should be interpreted. This should usually be the time when the text was
594080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *      originally composed. If no reference time is set, now is used.
595080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             *
596080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * @return this builder
597080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             */
598080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            @NonNull
599080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            public Builder setReferenceTime(@Nullable ZonedDateTime referenceTime) {
600080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                mReferenceTime = referenceTime;
601080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                return this;
602080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            }
603080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
604080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            /**
605080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             * Builds and returns the request object.
606080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki             */
607080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            @NonNull
608080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            public Request build() {
609080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                return new Request(mText, mStartIndex, mEndIndex, mDefaultLocales, mReferenceTime);
610080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            }
611080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        }
612080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki
6130d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        @Override
6140d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        public int describeContents() {
6150d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus            return 0;
6160d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        }
6170d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
6180d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        @Override
6190d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        public void writeToParcel(Parcel dest, int flags) {
620080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            dest.writeString(mText.toString());
621080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            dest.writeInt(mStartIndex);
622080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            dest.writeInt(mEndIndex);
6230d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus            dest.writeInt(mDefaultLocales != null ? 1 : 0);
6240d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus            if (mDefaultLocales != null) {
6250d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus                mDefaultLocales.writeToParcel(dest, flags);
6260d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus            }
627705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus            dest.writeInt(mReferenceTime != null ? 1 : 0);
628705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus            if (mReferenceTime != null) {
629a1652cfcce547183a426cc710691c740b2e46aa7Jan Althaus                dest.writeString(mReferenceTime.toString());
630705b9e9a1b435c7b8ab3b47d300ced487ed2262eJan Althaus            }
6310d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        }
6320d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
633080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        public static final Parcelable.Creator<Request> CREATOR =
634080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                new Parcelable.Creator<Request>() {
6350d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus                    @Override
636080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                    public Request createFromParcel(Parcel in) {
637080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                        return new Request(in);
6380d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus                    }
6390d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
6400d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus                    @Override
641080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                    public Request[] newArray(int size) {
642080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki                        return new Request[size];
6430d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus                    }
6440d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus                };
6450d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
646080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        private Request(Parcel in) {
647080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mText = in.readString();
648080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mStartIndex = in.readInt();
649080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mEndIndex = in.readInt();
650080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mDefaultLocales = in.readInt() == 0 ? null : LocaleList.CREATOR.createFromParcel(in);
651080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki            mReferenceTime = in.readInt() == 0 ? null : ZonedDateTime.parse(in.readString());
6520d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus        }
6530d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus    }
6540d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
655d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    @Override
656d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    public int describeContents() {
657d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki        return 0;
658d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    }
6590d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
660d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    @Override
661d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    public void writeToParcel(Parcel dest, int flags) {
662d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki        dest.writeString(mText);
663ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        // NOTE: legacy fields are not parcelled.
66420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        dest.writeTypedList(mActions);
665d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki        mEntityConfidence.writeToParcel(dest, flags);
666080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        dest.writeString(mId);
667d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    }
6680d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
669d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    public static final Parcelable.Creator<TextClassification> CREATOR =
670d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki            new Parcelable.Creator<TextClassification>() {
671d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                @Override
672d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                public TextClassification createFromParcel(Parcel in) {
673d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                    return new TextClassification(in);
674d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                }
6750d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
676d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                @Override
677d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                public TextClassification[] newArray(int size) {
678d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                    return new TextClassification[size];
679d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki                }
680d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki            };
6810d9fbb9bd15fb1c6eae171d316a2de65aaffeb48Jan Althaus
682d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki    private TextClassification(Parcel in) {
683d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki        mText = in.readString();
684ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        mActions = in.createTypedArrayList(RemoteAction.CREATOR);
685ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        if (!mActions.isEmpty()) {
686ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            final RemoteAction action = mActions.get(0);
687ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            mLegacyIcon = maybeLoadDrawable(action.getIcon());
688ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            mLegacyLabel = action.getTitle().toString();
689ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            mLegacyOnClickListener = createIntentOnClickListener(mActions.get(0).getActionIntent());
69020d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        } else {
691ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            mLegacyIcon = null;
692ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            mLegacyLabel = null;
693ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            mLegacyOnClickListener = null;
69420d346eafec9404fb6f5b8eeb9a18ad794b4ca9aJan Althaus        }
695ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        mLegacyIntent = null; // mLegacyIntent is not parcelled.
696d32906c202db3b84151c310ecd89a07bb41208f7Abodunrinwa Toki        mEntityConfidence = EntityConfidence.CREATOR.createFromParcel(in);
697080c8542b68cf17a0441862c404cb49ce0e86cfeAbodunrinwa Toki        mId = in.readString();
6982b6020fc80dc239114ecc7ecd501d382d4883641Abodunrinwa Toki    }
699ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
700ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki    // Best effort attempt to try to load a drawable from the provided icon.
701ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki    @Nullable
702ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki    private static Drawable maybeLoadDrawable(Icon icon) {
703ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        if (icon == null) {
704ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            return null;
705ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        }
706ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        switch (icon.getType()) {
707ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            case Icon.TYPE_BITMAP:
708ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                return new BitmapDrawable(Resources.getSystem(), icon.getBitmap());
709ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            case Icon.TYPE_ADAPTIVE_BITMAP:
710ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                return new AdaptiveIconDrawable(null,
711ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                        new BitmapDrawable(Resources.getSystem(), icon.getBitmap()));
712ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki            case Icon.TYPE_DATA:
713ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                return new BitmapDrawable(
714ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                        Resources.getSystem(),
715ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                        BitmapFactory.decodeByteArray(
716ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki                                icon.getDataBytes(), icon.getDataOffset(), icon.getDataLength()));
717ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        }
718ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki        return null;
719ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki    }
720ba196c5a3d8a8f04ffb22fd29435e545ee435fa0Abodunrinwa Toki
721ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki    // TODO: Remove once apps can build against the latest sdk.
722ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki    /**
723ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki     * Optional input parameters for generating TextClassification.
724ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki     * @hide
725ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki     */
726ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki    public static final class Options {
727ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
728ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable private final TextClassificationSessionId mSessionId;
729ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable private final Request mRequest;
730ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable private LocaleList mDefaultLocales;
731ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable private ZonedDateTime mReferenceTime;
732ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
733ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public Options() {
734ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            this(null, null);
735ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
736ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
737ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        private Options(
738ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki                @Nullable TextClassificationSessionId sessionId, @Nullable Request request) {
739ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            mSessionId = sessionId;
740ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            mRequest = request;
741ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
742ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
743ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        /** Helper to create Options from a Request. */
744ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public static Options from(TextClassificationSessionId sessionId, Request request) {
745ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            final Options options = new Options(sessionId, request);
746ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            options.setDefaultLocales(request.getDefaultLocales());
747ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            options.setReferenceTime(request.getReferenceTime());
748ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return options;
749ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
750ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
751ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        /** @param defaultLocales ordered list of locale preferences. */
752ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public Options setDefaultLocales(@Nullable LocaleList defaultLocales) {
753ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            mDefaultLocales = defaultLocales;
754ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return this;
755ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
756ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
757ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        /** @param referenceTime refrence time used for interpreting relatives dates */
758ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public Options setReferenceTime(@Nullable ZonedDateTime referenceTime) {
759ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            mReferenceTime = referenceTime;
760ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return this;
761ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
762ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
763ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable
764ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public LocaleList getDefaultLocales() {
765ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return mDefaultLocales;
766ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
767ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
768ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable
769ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public ZonedDateTime getReferenceTime() {
770ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return mReferenceTime;
771ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
772ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
773ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable
774ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public Request getRequest() {
775ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return mRequest;
776ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
777ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki
778ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        @Nullable
779ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        public TextClassificationSessionId getSessionId() {
780ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki            return mSessionId;
781ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki        }
782ae82e7ad280e55dca22014c6abc857372229f89cAbodunrinwa Toki    }
783f001fefff3745c29e2ff6903d69ad921df1ea277Abodunrinwa Toki}
784