1/*
2 * Copyright (C) 2006 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
17package android.text.style;
18
19import android.annotation.NonNull;
20import android.content.ActivityNotFoundException;
21import android.content.Context;
22import android.content.Intent;
23import android.net.Uri;
24import android.os.Parcel;
25import android.provider.Browser;
26import android.text.ParcelableSpan;
27import android.text.TextUtils;
28import android.util.Log;
29import android.view.View;
30
31/**
32 * Implementation of the {@link ClickableSpan} that allows setting a url string. When
33 * selecting and clicking on the text to which the span is attached, the <code>URLSpan</code>
34 * will try to open the url, by launching an an Activity with an {@link Intent#ACTION_VIEW} intent.
35 * <p>
36 * For example, a <code>URLSpan</code> can be used like this:
37 * <pre>
38 * SpannableString string = new SpannableString("Text with a url span");
39 * string.setSpan(new URLSpan("http://www.developer.android.com"), 12, 15, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
40 * </pre>
41 * <img src="{@docRoot}reference/android/images/text/style/urlspan.png" />
42 * <figcaption>Text with <code>URLSpan</code>.</figcaption>
43 */
44public class URLSpan extends ClickableSpan implements ParcelableSpan {
45
46    private final String mURL;
47
48    /**
49     * Constructs a {@link URLSpan} from a url string.
50     *
51     * @param url the url string
52     */
53    public URLSpan(String url) {
54        mURL = url;
55    }
56
57    /**
58     * Constructs a {@link URLSpan} from a parcel.
59     */
60    public URLSpan(@NonNull Parcel src) {
61        mURL = src.readString();
62    }
63
64    @Override
65    public int getSpanTypeId() {
66        return getSpanTypeIdInternal();
67    }
68
69    /** @hide */
70    @Override
71    public int getSpanTypeIdInternal() {
72        return TextUtils.URL_SPAN;
73    }
74
75    @Override
76    public int describeContents() {
77        return 0;
78    }
79
80    @Override
81    public void writeToParcel(@NonNull Parcel dest, int flags) {
82        writeToParcelInternal(dest, flags);
83    }
84
85    /** @hide */
86    @Override
87    public void writeToParcelInternal(@NonNull Parcel dest, int flags) {
88        dest.writeString(mURL);
89    }
90
91    /**
92     * Get the url string for this span.
93     *
94     * @return the url string.
95     */
96    public String getURL() {
97        return mURL;
98    }
99
100    @Override
101    public void onClick(View widget) {
102        Uri uri = Uri.parse(getURL());
103        Context context = widget.getContext();
104        Intent intent = new Intent(Intent.ACTION_VIEW, uri);
105        intent.putExtra(Browser.EXTRA_APPLICATION_ID, context.getPackageName());
106        try {
107            context.startActivity(intent);
108        } catch (ActivityNotFoundException e) {
109            Log.w("URLSpan", "Actvity was not found for intent, " + intent.toString());
110        }
111    }
112}
113