Skip to content

Commit

Permalink
Add linkifyHTML() methods for Html.fromHTML() links
Browse files Browse the repository at this point in the history
  • Loading branch information
saket committed Oct 15, 2016
1 parent 7519dc9 commit a2e6469
Show file tree
Hide file tree
Showing 6 changed files with 167 additions and 36 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
public class BetterLinkMovementMethod extends LinkMovementMethod {

private static final Class SPAN_CLASS = ClickableSpan.class;
private static final int LINKIFY_NONE = -2;
private static BetterLinkMovementMethod singleInstance;

private OnLinkClickListener onLinkClickListener;
Expand Down Expand Up @@ -62,12 +63,21 @@ public static BetterLinkMovementMethod newInstance() {
public static BetterLinkMovementMethod linkify(int linkifyMask, TextView... textViews) {
BetterLinkMovementMethod movementMethod = newInstance();
for (TextView textView : textViews) {
textView.setMovementMethod(movementMethod);
Linkify.addLinks(textView, linkifyMask);
addLinks(linkifyMask, movementMethod, textView);
}
return movementMethod;
}

/**
* Like {@link #linkify(int, TextView...)}, but can be used for TextViews with HTML links.
*
* @param textViews The TextViews on which a {@link BetterLinkMovementMethod} should be registered.
* @return The registered {@link BetterLinkMovementMethod} on the TextViews.
*/
public static BetterLinkMovementMethod linkifyHTML(TextView... textViews) {
return linkify(LINKIFY_NONE, textViews);
}

/**
* Recursively register a {@link BetterLinkMovementMethod} on every TextView inside a layout.
*
Expand All @@ -77,24 +87,17 @@ public static BetterLinkMovementMethod linkify(int linkifyMask, TextView... text
*/
public static BetterLinkMovementMethod linkify(int linkifyMask, ViewGroup viewGroup) {
BetterLinkMovementMethod movementMethod = newInstance();
rLinkify(linkifyMask, viewGroup, movementMethod);
rAddLinks(linkifyMask, viewGroup, movementMethod);
return movementMethod;
}

private static void rLinkify(int linkifyMask, ViewGroup viewGroup, BetterLinkMovementMethod movementMethod) {
for (int i = 0; i < viewGroup.getChildCount(); i++) {
View child = viewGroup.getChildAt(i);

if (child instanceof ViewGroup) {
// Recursively find child TextViews.
rLinkify(linkifyMask, ((ViewGroup) child), movementMethod);

} else if (child instanceof TextView) {
TextView textView = (TextView) child;
textView.setMovementMethod(movementMethod);
Linkify.addLinks(textView, linkifyMask);
}
}
/**
* Like {@link #linkify(int, TextView...)}, but can be used for TextViews with HTML links.
*
* @return The registered {@link BetterLinkMovementMethod} on the TextViews.
*/
public static BetterLinkMovementMethod linkifyHTML(ViewGroup viewGroup) {
return linkify(LINKIFY_NONE, viewGroup);
}

/**
Expand All @@ -107,7 +110,41 @@ private static void rLinkify(int linkifyMask, ViewGroup viewGroup, BetterLinkMov
public static BetterLinkMovementMethod linkify(int linkifyMask, Activity activity) {
// Find the layout passed to setContentView().
ViewGroup activityLayout = ((ViewGroup) ((ViewGroup) activity.findViewById(Window.ID_ANDROID_CONTENT)).getChildAt(0));
return linkify(linkifyMask, activityLayout);

BetterLinkMovementMethod movementMethod = newInstance();
rAddLinks(linkifyMask, activityLayout, movementMethod);
return movementMethod;
}

/**
* Like {@link #linkify(int, TextView...)}, but can be used for TextViews with HTML links.
*
* @return The registered {@link BetterLinkMovementMethod} on the TextViews.
*/
public static BetterLinkMovementMethod linkifyHTML(Activity activity) {
return linkify(LINKIFY_NONE, activity);
}

private static void rAddLinks(int linkifyMask, ViewGroup viewGroup, BetterLinkMovementMethod movementMethod) {
for (int i = 0; i < viewGroup.getChildCount(); i++) {
View child = viewGroup.getChildAt(i);

if (child instanceof ViewGroup) {
// Recursively find child TextViews.
rAddLinks(linkifyMask, ((ViewGroup) child), movementMethod);

} else if (child instanceof TextView) {
TextView textView = (TextView) child;
addLinks(linkifyMask, movementMethod, textView);
}
}
}

private static void addLinks(int linkifyMask, BetterLinkMovementMethod movementMethod, TextView textView) {
if (linkifyMask != LINKIFY_NONE) {
textView.setMovementMethod(movementMethod);
Linkify.addLinks(textView, linkifyMask);
}
}

/**
Expand Down
2 changes: 1 addition & 1 deletion sample/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -32,5 +32,5 @@ android {
}

dependencies {
compile 'me.saket:better-link-movement-method:1.0'
compile project(path: ':better-link-movement-method')
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,26 +2,39 @@

import android.app.Activity;
import android.os.Bundle;
import android.text.Html;
import android.text.util.Linkify;
import android.widget.TextView;
import android.widget.Toast;

import me.saket.bettermovementmethod.BetterLinkMovementMethod;

@SuppressWarnings("deprecation")
public class MainActivity extends Activity {

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

TextView textView1 = (TextView) findViewById(R.id.text1);
BetterLinkMovementMethod.OnLinkClickListener urlClickListener = (view, url) -> {
if (isPhoneNumber(url)) {
FloatingMenu.show(this, view, url);
} else {
Toast.makeText(this, url, Toast.LENGTH_SHORT).show();
}

BetterLinkMovementMethod
.linkify(Linkify.PHONE_NUMBERS, textView1)
.setOnLinkClickListener((view, url) -> {
FloatingMenu.show(this, view, url);
return true;
});
return true;
};
BetterLinkMovementMethod.linkify(Linkify.ALL, this).setOnLinkClickListener(urlClickListener);

TextView gothamTextView = (TextView) findViewById(android.R.id.text1);
gothamTextView.setText(Html.fromHtml(getString(R.string.bettermovementmethod_dummy_text_long)));
BetterLinkMovementMethod.linkifyHTML(gothamTextView).setOnLinkClickListener(urlClickListener);
}

private boolean isPhoneNumber(String url) {
return url.endsWith(getString(R.string.bettermovementmethod_dummy_number));
}

}
67 changes: 58 additions & 9 deletions sample/src/main/res/layout/activity_main.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,65 @@
android:layout_height="match_parent"
android:orientation="vertical"
android:padding="16dp"
tools:context=".MainActivity">
tools:context=".MainActivity"
tools:ignore="HardcodedText">

<TextView
android:id="@+id/text1"
<FrameLayout style="@style/BetterLinkMovementMethodContainer">

<TextView
android:id="@android:id/text1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:lineSpacingExtra="8dp"
android:text="@string/bettermovementmethod_dummy_text_long" />
</FrameLayout>

<LinearLayout
style="@style/BetterLinkMovementMethodContainer"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:layout_marginBottom="8dp"
android:background="#413f3f"
android:gravity="center"
android:padding="48dp"
android:text="@string/bettermovementmethod_dummy_text" />
android:layout_marginTop="16dp"
android:baselineAligned="false"
android:orientation="horizontal">

<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
android:paddingTop="4dp">

<TextView
style="@style/BetterLinkMovementMethodSubtitle"
android:text="Phone" />

<TextView
style="@style/BetterLinkMovementMethodSubtitle"
android:layout_marginTop="12dp"
android:text="Email" />

<TextView
style="@style/BetterLinkMovementMethodSubtitle"
android:layout_marginTop="12dp"
android:text="Location" />
</LinearLayout>

<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical">

<TextView
style="@style/BetterLinkMovementMethodText"
android:text="@string/bettermovementmethod_dummy_number" />

<TextView
style="@style/BetterLinkMovementMethodText"
android:text="[email protected]" />

<TextView
style="@style/BetterLinkMovementMethodText"
android:text="https://goo.gl/maps/KfRBC6KLHA12" />
</LinearLayout>
</LinearLayout>
</LinearLayout>
7 changes: 6 additions & 1 deletion sample/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
<resources>
<string name="bettermovementmethod_app_name">BetterLinkMovement</string>
<string name="bettermovementmethod_dummy_text">When a forest grows too wild, a purging fire is inevitable and natural. 7899859911</string>
<string name="bettermovementmethod_dummy_text_long"><![CDATA[
<a href="https://en.wikipedia.org/wiki/Gotham_City">Gotham</a> has been good to our family, but the city\u2019s been suffering. People less fortunate
than us have been enduring very hard times. So we built a new, cheap, public transportation system to unite the city. And at the center,
<a href="http://batman.wikia.com/wiki/Wayne_Tower_(Nolan_Films)">Wayne tower</a>.
]]></string>
<string name="bettermovementmethod_dummy_number">7899859911</string>
</resources>
27 changes: 27 additions & 0 deletions sample/src/main/res/values/styles.xml
Original file line number Diff line number Diff line change
Expand Up @@ -17,4 +17,31 @@
<item name="android:paddingLeft">16dp</item>
<item name="android:paddingRight">16dp</item>
</style>

<style name="BetterLinkMovementMethodSubtitle">
<item name="android:layout_width">wrap_content</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:layout_marginRight">16dp</item>
<item name="android:layout_marginEnd">16dp</item>
<item name="android:fontFamily">sans-serif-smallcaps</item>
<item name="android:textStyle">bold</item>
<item name="android:textSize">12sp</item>
<item name="android:textAllCaps">true</item>
</style>

<style name="BetterLinkMovementMethodText">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:textColor">#eee</item>
<item name="android:layout_marginBottom">8dp</item>
</style>

<style name="BetterLinkMovementMethodContainer">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:orientation">vertical</item>
<item name="android:padding">16dp</item>
<item name="android:background">#413F3F</item>
</style>

</resources>

0 comments on commit a2e6469

Please sign in to comment.