String Manipulation Using SpannableString, Regular Expression, Pattern Matcher and Custom TextView in Android-Part1.
In this short article, we are going to look at string manipulation in android using SpannableString, Regular Expression and Custom TextView.
- Go to your android studio and create the normal default project so you have the MainActivity only. Create a folder called view so that we can create our Custom TexView inside the folder.
- Create a Java class called MyTextView inside the view folder, extend TextView and override setText() as shown below.
public class MyTextView extends TextView {
public MyTextView(Context context) {
super(context);
} public MyTextView(Context context, AttributeSet attrs) {
super(context, attrs);
} public MyTextView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
} @Override
public void setText(CharSequence text, BufferType type) {
super.setText(text, type);
}
}
4. Modify the activity_main.xml.
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="jerryhanks.me.strings.MainActivity"> <jerryhanks.me.strings.view.MyTextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:text="Hello World!"
android:textAppearance="@style/Base.TextAppearance.AppCompat.Medium" />
</RelativeLayout>
5. Modify the MainActivity to be what we have below.
public class MainActivity extends AppCompatActivity { @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
MyTextView mTextView = (MyTextView) findViewById(R.id.string_tv);
StringBuilder sampleString = new StringBuilder();
sampleString.append("Bold Span\n");
sampleString.append("Foreground Span\n");
sampleString.append("Background Span\n");
sampleString.append("Clickable Span\n");
sampleString.append("Url Span: Google.com\n");
sampleString.append("S Subscript\n");
sampleString.append("S SuperScript\n");
sampleString.append("Underline Me\n");
sampleString.append("Relative TextSize span\n");
sampleString.append("Italicize me\n");
sampleString.append("Strike Me Though\n"); //build the spannable String
SpannableString spannableString = new SpannableString(sampleString.toString());
mTextView.setText(spannableString,TextView.BufferType.SPANNABLE); }
}
RESULT: If we run the app, we have the screen shown below, no span applied yet, it is time to start applying the spans.
6. Add StyleSpan(Bold Style).
To add span, call the spannableString method setSpan(arg1, arg2 arg3, arg 4), where arg2 is the type of Spannable which you will see soon, the arg 2 and 3 are integers which are for start and end while the arg3 is the Flag for the Spannable also an integer.
So before calling the textView method set text, add the following line of code.
spannableString.setSpan(new StyleSpan(Typeface.BOLD),0,11,0);
Run the app and you will see the first text is in bold.
7. Add ForegroundColorSpan.
So let's add foreground span to the TextView starting from the second string, we shall set the foreground to be the accent colour. So before calling the setText() method, add the following line of code.
//add fore ground span
spannableString.setSpan(new ForegroundColorSpan(
ContextCompat.getColor(getApplicationContext(), R.color.colorAccent)),
10, 26, 0);
Run the app and we have the output shown below.
8. Add BackgroundColorSpan.
Follow the same way and the following line of code to get A Background span.
//adding background Span
spannableString.setSpan(new BackgroundColorSpan(
ContextCompat.getColor(getApplicationContext(), R.color.colorPrimary)), 26, 42, 0);
Run the app and we have the output shown below:
9. Add ClickableSpan.
Follow the same steps and add the following lines of code:
//adding click span
ClickableSpan clickableSpan = new ClickableSpan() {
@Override
public void onClick(View view) {
//what happens whe i click
Toast.makeText(getApplicationContext(), "you just clicked on a Click Span!", Toast.LENGTH_LONG).show(); }
};
spannableString.setSpan(clickableSpan, 45, 61, 0);
If you run the app, you will observe that nothing happens when you click on the ClickableSpan, this is because one thing is missing, we need to set the Movement method of the textView so that it can detect the Clicks. this can be done in the constructor of our Custom TextView or on the fly, so let's do it on the fly.
Add this line of code after the one above.
//set the movement method for the TextView
mTextView.setMovementMethod(LinkMovementMethod.getInstance());
Run the app again, we have the output shown below:
10. Add URLSpan.
Now let's add a Url span that will open the site: https://www.google.com.
Follow the same steps and add the following lines of code to the main activity. You will notice that we override the onClick() method so that we can specify what happens to the link when it is clicked.
//add Url Span
URLSpan urlSpan = new URLSpan("https://www.google.com") {
@Override
public void onClick(View widget) {
Intent urlIntent = new Intent(Intent.ACTION_VIEW);
urlIntent.setData(Uri.parse(getURL()));
startActivity(urlIntent);
}
};spannableString.setSpan(urlSpan, 61, 83, 0);
Run the app and click on the URL, it will start the activity to open the url in a browser.
11. AddSubScript Span
Follow the same steps and add the following lines of code:
//add subscript Span
spannableString.setSpan(new SubscriptSpan(), 79, 89, 0);
Run the App and you will have the output shown below:
12. Add Superscript Span
Follow the same steps and add the following lines of code:
//add Superscript span
spannableString.setSpan(new SuperscriptSpan(),92,104,0);
Run the App and you will have the output shown below:
14. Add Underline Span
Follow the same steps and add the following lines of codes.
//add underline span
spannableString.setSpan(new UnderlineSpan(), 104, 116, 0);
Run the App and you will have the output shown below:
15. Add RelativeSizeSpan
Follow the same steps and add the following lines of code
//add relative size span
spannableString.setSpan(new RelativeSizeSpan(1.5f), 116, 139, 0);
Note that the relative span takes an argument which id of type float, this is the desired size relative to the main TexView size.
Run the app, you will have the output shown below:
17. Add StyleSpan(Italics)
Follow the same steps and add the following lines of codes:
//add italics span
spannableString.setSpan(new StyleSpan(Typeface.ITALIC), 139, 152, 0);
Run the app and you will have the output shown below:
18. Add StrikeThroughSpan
Follow the same steps and add the following lines of code:
//add strike through span
spannableString.setSpan(new StrikethroughSpan(), 153, 170, 0);
Run the Code and you will get the output shown below:
19. Using Regular Expression.
In the second part of this app, we shall use regular expressions to detect some string patters which corresponds to Bible links. So we shall consider the following patterns:
- John 3:16 — Single verse
- John 3:16–18 — Verse Range
- 1 Corinthians 3:4 — single verse with a prefix
- 2 Corinthians 4:6–8 verse Range with a prefix
For this purpose, we shall create another custom view which implements this functionality so that we can just re-use it.
Create a new custom textView called BibleTextView and add the lines of code shown below:
public class BibleTextView extends TextView {
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public BibleTextView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
init();
}
public BibleTextView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init();
} public BibleTextView(Context context, AttributeSet attrs) {
super(context, attrs);
init();
} public BibleTextView(Context context) {
super(context);
init();
} private void init() {
setMovementMethod(LinkMovementMethod.getInstance());
} @Override
public void setText(CharSequence text, BufferType type) {
//define the matchin pattern
Pattern pattern = Pattern
.compile("((\\d)?\\s?(John|Corinthians)\\s+(\\d*)(:)?\\s*(\\d*)(\\s*(-|–)\\s*(\\d*))?)"
, Pattern.CASE_INSENSITIVE);
//build a spannable String using the Consequence
SpannableString spString = new SpannableString(text);
Matcher matcher = pattern.matcher(text);
while (matcher.find()) {
int start = matcher.start();
int end = matcher.end();
ClickableSpan clickSpan = new ClickableSpan() {
@Override
public void onClick(View view) {
Toast.makeText(getContext(), "You jus clicked on a Bible link", Toast.LENGTH_LONG).show();
}
};
spString.setSpan(clickSpan, start, end, 0);
} super.setText(spString, BufferType.SPANNABLE);
}
}
Modify the MainActivity.java and add the following lines of code:
BibleTextView mBibleTv = (BibleTextView) findViewById(R.id.bible_tv);StringBuilder bibleString = new StringBuilder("This is the bible TextView: Open John 3:16")
.append(" and the John 3:16-18")
.append(" and then 1 Corinthians 3:4")
.append(" and the 2 Corinthians 4:6-8 and then we are ready to go with string manipulation.");mBibleTv.setText(bibleString);
Run the App again, we have the output shown below:
That is all for the first part of String manipulation, in part 2 to follow, we shall go deep into Regular expression, discuss Patterns and Matchers in detail.
If you find this article useful, don’t forget to recommend it, and share it with friends.
You can check out the following links to find out more about Android SpannableString and Regular Expressions.
- http://androidcocktail.blogspot.com.ng/2014/03/android-spannablestring-example.html
- http://www.vogella.com/tutorials/JavaRegularExpressions/article.html
- https://developer.android.com/reference/java/util/regex/Pattern.html
- https://developer.android.com/reference/java/util/regex/Matcher.html
The entire code is available here on Github.