特定文字をリンクするTextView
特定の文字をリンクにしたいときに使うTextView
LinkableTextView.kt
class LinkableTextView @JvmOverloads constructor( context: Context, attrs: AttributeSet? = null ) : TextView(context, attrs) { private var target = "" private var color = 0 private var linkBold = false var listener: Listener? = null init { val a = context.theme.obtainStyledAttributes( attrs, R.styleable.LinkableTextView, 0, 0) try { target = a.getString(R.styleable.LinkableTextView_target) color = a.getColor(R.styleable.LinkableTextView_link_color, 0) linkBold = a.getBoolean(R.styleable.LinkableTextView_link_bold, false) } finally { a.recycle() } } override fun setText(text: CharSequence?, type: BufferType?) { if (TextUtils.isEmpty(target)) { super.setText(text, type) return } val p1 = Pattern.compile(target) val m1 = p1.matcher(text) val ss = SpannableString(text) if (m1.find()) { val start = m1.start() val end = m1.end() movementMethod = LinkMovementMethod.getInstance() ss.setSpan(object : ClickableSpan() { override fun onClick(widget: View) { listener?.onLinkClick() } }, start, end, Spanned.SPAN_INCLUSIVE_INCLUSIVE) if (color != 0) { ss.setSpan(ForegroundColorSpan(color), start, end, Spanned.SPAN_INCLUSIVE_INCLUSIVE) } if (linkBold) { ss.setSpan(StyleSpan(Typeface.BOLD), start, end, Spanned.SPAN_INCLUSIVE_INCLUSIVE) } } super.setText(ss, type) } interface Listener { fun onLinkClick() } }
attr.xml
から要素を取得しその値に応じてリンクさせたい文字列や見た目を設定していきます。
target
はリンクさせたい文字列、color
はリンクさせたい文字列の色、linkBold
リンクさせたい文字列がBoldかどうか
を指定します。
attrs.xml
<?xml version="1.0" encoding="utf-8"?> <resources> <declare-styleable name="LinkableTextView"> <attr name="link_color" format="color"/> <attr name="target" format="string"/> <attr name="link_bold" format="boolean"/> </declare-styleable> </resources>
上記した3つの要素を指定しています。
使い方
xmlで置くときに3つの要素に値を設定します。
<LinkableTextView android:id="@+id/id" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="20sp" android:text="text" android:textColor="@color/your_color" app:target="target" app:link_color="@color/your_color" />
コードでリンクをクリックした際の動作を書きます。
binding.linkableTextView.text = "text" binding.linkableTextViewlistener = object: LinkableTextView.Listener { override fun onLinkClick() { //do something } }