SpannableStringとは?
概要
・文字列にさまざまな装飾やスタイル設定を行えるようにするためのもの
・一つの文字列に対して複数のスタイルを適用させることができる
注意点
・例として掲載しているコードはViewBindingを使用しています
(変数b
として定義しています)
主な種類
クラス名 | 概要 |
---|---|
ForgroundColorSpan | テキストの色を変更する |
BackgroundColorSpan | テキストの背景色を変更する |
StyleSpan | テキストを太文字やイタリックにする |
TypefaceSpan | 指定フォントを適用する |
RelativeSizeSpan | テキストのサイズを相対的に変更する |
AbsoluteSizeSpan | テキストのサイズを絶対値で変更する |
URLSpan | テキストをリンクにする |
UnderlineSpan | テキストに下線を引く |
StrikethroughSpan | テキストに取り消し線を引く |
ImageSpan | テキストを指定した文字に置き換える |
・他にもクリック可能にして、任意のアクションを実行するClickableSpan
や、インデントを設定するLeadingMarginSpan
、箇条書きの丸を追加するBulletSpan
などもあります
使い方
どのSpanクラスを使用するにしても、スタイルを適用する流れは共通です
- SpannnableStringに文字列を渡す
- SpannableString.setSpanを使用して文字列に装飾する
- TextViewなどに文字列を渡す
例: 文字列に下線を引きたい場合
fun underLineSpan(){
val sampleText = "このテキストに下線を引きます"
//textをSpannableStringにする
val spannableString = SpannableString(sampleText)
//setSpanメソッドを使用してスタイルを設定
spannableString.setSpan(
UnderlineSpan(),
0,
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
//TextViewに文字列を渡す
b.underLineText.text = spannableString
}
setSpan
について
・setSpanメソッドには4つの引数があります
- 適用するSpanクラス
- 適用を開始する文字のindex
- 適用を終了する文字のindex
- Span範囲の扱い方を指定するフラグ
・3の終了のインデックスに関しては指定したインデックス-1までの箇所に適用されます
例: 文字列が HelloWorld
の場合
spannableString.setSpan(
UnderlineSpan(), //使用するSpanクラス
0, //開始のインデックス
5, //終了のインデックス
Spannable.SPAN_EXCLUSIVE_INCLUSIVE //終了のインデックスを含まない
)
とすると、
このように下線が引かれます
サンプル
・UnderlineSpan
private fun setUnderSpan() {
val sampleText = "ここが重要です"
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
UnderlineSpan(),
0,
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.underLineText.text = spannableString
}
・ForegroundColorSpan
private fun setForegroundColorSpan() {
val sampleText = "Black and Red Text."
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
ForegroundColorSpan(Color.RED),
sampleText.indexOf('R'),
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.textColorText.text = spannableString
}
・BackgroundColorSpan
private fun setBackgroundSpan() {
val sampleText = "change Background Color."
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
BackgroundColorSpan(Color.RED),
sampleText.indexOf('B'),
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.backGroundColorText.text = spannableString
}
・StyleSpan
fun setTextStyleSpan() {
val sampleText = "通常の文字と太文字"
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
StyleSpan(Typeface.BOLD),
sampleText.indexOf('太'),
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.styleText.text = spannableString
}
・RelativeSizeSpan
fun setRelativeSizeSpan() {
val sampleText = "normal text size and big size text."
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
RelativeSizeSpan(2f), //元の文字サイズの2倍
sampleText.indexOf('b'),
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.relativeText.text = spannableString
}
・StrikethroughSpan
fun setStrikethroughSpan() {
val sampleText = "Original price $100"
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
StrikethroughSpan(),
0,
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.strikeThroughText.text = spannableString
}
・ImageSpan
fun setImageSpan() {
val sampleText = "Hello,Android."
val spannableString = SpannableString(sampleText)
spannableString.setSpan(
ImageSpan(this@MainActivity, android.R.drawable.sym_def_app_icon),
sampleText.indexOf('A'),
sampleText.length,
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
)
b.imageSpanText.text = spannableString
}
余談
・一部のものに関してはSpannableStringを使用しない方法でも再現できます
アンダーラインについて
・文字列があらかじめ決まっている場合、res/values/strings.xml内で
<resources>
<string name="underline_text"><u>下線</u>を引きます</string>
</resources>
このように<u>
タグで下線を引くことでできます
URLリンクについて
TextViewで、
<TextView
android:autoLink="web"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
このようにautoLink
にweb
を指定することで自動的にURLをリンクにできます
また、autoLink
は他にも電話番号やemailなどもリンクにできます
詳細・参照
・SpannableStringクラス
https://developer.android.com/reference/kotlin/android/text/SpannableString
・Spannableクラス
https://developer.android.com/reference/android/text/Spannable
・Android developers ガイド
https://developer.android.com/develop/ui/views/text-and-emoji/spans?hl=ja