Home | History | Annotate | Download | only in chooser
      1 /*
      2  * Copyright (C) 2015 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 
     18 package android.service.chooser;
     19 
     20 import android.annotation.Nullable;
     21 import android.content.ComponentName;
     22 import android.content.Intent;
     23 import android.content.IntentFilter;
     24 import android.graphics.drawable.Icon;
     25 import android.os.Bundle;
     26 import android.os.Parcel;
     27 import android.os.Parcelable;
     28 
     29 /**
     30  * A ChooserTarget represents a deep-link into an application as returned by a
     31  * {@link android.service.chooser.ChooserTargetService}.
     32  *
     33  * <p>A chooser target represents a specific deep link target into an application exposed
     34  * for selection by the user. This might be a frequently emailed contact, a recently active
     35  * group messaging conversation, a folder in a cloud storage app, a collection of related
     36  * items published on a social media service or any other contextually relevant grouping
     37  * of target app + relevant metadata.</p>
     38  *
     39  * <p>Creators of chooser targets should consult the relevant design guidelines for the type
     40  * of target they are presenting. For example, targets involving people should be presented
     41  * with a circular icon.</p>
     42  */
     43 public final class ChooserTarget implements Parcelable {
     44     private static final String TAG = "ChooserTarget";
     45 
     46     /**
     47      * The title of this target that will be shown to the user. The title may be truncated
     48      * if it is too long to display in the space provided.
     49      */
     50     private CharSequence mTitle;
     51 
     52     /**
     53      * The icon that will be shown to the user to represent this target.
     54      * The system may resize this icon as appropriate.
     55      */
     56     private Icon mIcon;
     57 
     58     /**
     59      * The ComponentName of the Activity to be invoked. Must be part of the target creator's
     60      * own package or an Activity exported by its package.
     61      */
     62     private ComponentName mComponentName;
     63 
     64     /**
     65      * A Bundle to merge with the extras of the intent sent to this target.
     66      * Any extras here will override the extras from the original intent.
     67      */
     68     private Bundle mIntentExtras;
     69 
     70     /**
     71      * The score given to this item. It can be normalized.
     72      */
     73     private float mScore;
     74 
     75     /**
     76      * Construct a deep link target for presentation by a chooser UI.
     77      *
     78      * <p>A target is composed of a title and an icon for presentation to the user.
     79      * The UI presenting this target may truncate the title if it is too long to be presented
     80      * in the available space, as well as crop, resize or overlay the supplied icon.</p>
     81      *
     82      * <p>The creator of a target may supply a ranking score. This score is assumed to be relative
     83      * to the other targets supplied by the same
     84      * {@link ChooserTargetService#onGetChooserTargets(ComponentName, IntentFilter) query}.
     85      * Scores should be in the range from 0.0f (unlikely match) to 1.0f (very relevant match).
     86      * Scores for a set of targets do not need to sum to 1.</p>
     87      *
     88      * <p>The ComponentName must be the name of an Activity component in the creator's own
     89      * package, or an exported component from any other package. You may provide an optional
     90      * Bundle of extras that will be merged into the final intent before it is sent to the
     91      * target Activity; use this to add any additional data about the deep link that the target
     92      * activity will read. e.g. conversation IDs, email addresses, etc.</p>
     93      *
     94      * <p>Take care not to place custom {@link android.os.Parcelable} types into
     95      * the extras bundle, as the system will not be able to unparcel them to merge them.</p>
     96      *
     97      * @param title title of this target that will be shown to a user
     98      * @param icon icon to represent this target
     99      * @param score ranking score for this target between 0.0f and 1.0f, inclusive
    100      * @param componentName Name of the component to be launched if this target is chosen
    101      * @param intentExtras Bundle of extras to merge with the extras of the launched intent
    102      */
    103     public ChooserTarget(CharSequence title, Icon icon, float score,
    104             ComponentName componentName, @Nullable Bundle intentExtras) {
    105         mTitle = title;
    106         mIcon = icon;
    107         if (score > 1.f || score < 0.f) {
    108             throw new IllegalArgumentException("Score " + score + " out of range; "
    109                     + "must be between 0.0f and 1.0f");
    110         }
    111         mScore = score;
    112         mComponentName = componentName;
    113         mIntentExtras = intentExtras;
    114     }
    115 
    116     ChooserTarget(Parcel in) {
    117         mTitle = in.readCharSequence();
    118         if (in.readInt() != 0) {
    119             mIcon = Icon.CREATOR.createFromParcel(in);
    120         } else {
    121             mIcon = null;
    122         }
    123         mScore = in.readFloat();
    124         mComponentName = ComponentName.readFromParcel(in);
    125         mIntentExtras = in.readBundle();
    126     }
    127 
    128     /**
    129      * Returns the title of this target for display to a user. The UI displaying the title
    130      * may truncate this title if it is too long to be displayed in full.
    131      *
    132      * @return the title of this target, intended to be shown to a user
    133      */
    134     public CharSequence getTitle() {
    135         return mTitle;
    136     }
    137 
    138     /**
    139      * Returns the icon representing this target for display to a user. The UI displaying the icon
    140      * may crop, resize or overlay this icon.
    141      *
    142      * @return the icon representing this target, intended to be shown to a user
    143      */
    144     public Icon getIcon() {
    145         return mIcon;
    146     }
    147 
    148     /**
    149      * Returns the ranking score supplied by the creator of this ChooserTarget.
    150      * Values are between 0.0f and 1.0f. The UI displaying the target may
    151      * take this score into account when sorting and merging targets from multiple sources.
    152      *
    153      * @return the ranking score for this target between 0.0f and 1.0f, inclusive
    154      */
    155     public float getScore() {
    156         return mScore;
    157     }
    158 
    159     /**
    160      * Returns the ComponentName of the Activity that should be launched for this ChooserTarget.
    161      *
    162      * @return the name of the target Activity to launch
    163      */
    164     public ComponentName getComponentName() {
    165         return mComponentName;
    166     }
    167 
    168     /**
    169      * Returns the Bundle of extras to be added to an intent launched to this target.
    170      *
    171      * @return the extras to merge with the extras of the intent being launched
    172      */
    173     public Bundle getIntentExtras() {
    174         return mIntentExtras;
    175     }
    176 
    177     @Override
    178     public String toString() {
    179         return "ChooserTarget{"
    180                 + mComponentName
    181                 + ", " + mIntentExtras
    182                 + ", '" + mTitle
    183                 + "', " + mScore + "}";
    184     }
    185 
    186     @Override
    187     public int describeContents() {
    188         return 0;
    189     }
    190 
    191     @Override
    192     public void writeToParcel(Parcel dest, int flags) {
    193         dest.writeCharSequence(mTitle);
    194         if (mIcon != null) {
    195             dest.writeInt(1);
    196             mIcon.writeToParcel(dest, 0);
    197         } else {
    198             dest.writeInt(0);
    199         }
    200         dest.writeFloat(mScore);
    201         ComponentName.writeToParcel(mComponentName, dest);
    202         dest.writeBundle(mIntentExtras);
    203     }
    204 
    205     public static final Creator<ChooserTarget> CREATOR
    206             = new Creator<ChooserTarget>() {
    207         @Override
    208         public ChooserTarget createFromParcel(Parcel source) {
    209             return new ChooserTarget(source);
    210         }
    211 
    212         @Override
    213         public ChooserTarget[] newArray(int size) {
    214             return new ChooserTarget[size];
    215         }
    216     };
    217 }
    218