Skip to content

Instantly share code, notes, and snippets.

@janvde
Last active October 10, 2019 15:56

Revisions

  1. janvde revised this gist Apr 26, 2016. 1 changed file with 50 additions and 24 deletions.
    74 changes: 50 additions & 24 deletions StyledString.java
    Original file line number Diff line number Diff line change
    @@ -1,9 +1,13 @@
    import android.content.Context;
    import android.support.annotation.ColorRes;
    import android.support.annotation.Nullable;
    import android.support.annotation.StringRes;
    import android.support.annotation.StyleRes;
    import android.text.Spannable;
    import android.text.SpannableStringBuilder;
    import android.text.method.LinkMovementMethod;
    import android.text.style.ClickableSpan;
    import android.text.style.ForegroundColorSpan;
    import android.text.style.TextAppearanceSpan;
    import android.view.View;
    import android.widget.TextView;
    @@ -25,6 +29,9 @@ public interface OnSpanClickListener {
    private String fullString;
    private Context context;

    private int startingIndex;
    private int endingIndex;


    /**
    * constructor for string
    @@ -56,20 +63,10 @@ public StyledString(Context context, @StringRes int fullStringRes){
    * @return Styledstring
    */
    public StyledString put(String subString, @StyleRes int textAppearance){
    if(subString.length() > 0 && !subString.trim().equals("")) {

    //for counting start/end indexes
    int startingIndex = fullString.indexOf(subString);
    int endingIndex = startingIndex + subString.length();

    if(startingIndex < 0 || endingIndex <0){
    return this;
    }

    if(getStartEnd(subString)){
    TextAppearanceSpan textAppearanceSpan = new TextAppearanceSpan(context, textAppearance);
    fullStringBuilder.setSpan(textAppearanceSpan, startingIndex, endingIndex, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
    }

    return this;
    }

    @@ -82,17 +79,8 @@ public StyledString put(String subString, @StyleRes int textAppearance){
    * @param spanClickListener listener to listen for cliks, can be null
    * @return StyledString
    */
    public StyledString putLink(String subString, final OnSpanClickListener spanClickListener){
    if(subString.length() > 0 && !subString.trim().equals("")) {

    //for counting start/end indexes
    int startingIndex = fullString.indexOf(subString);
    int endingIndex = startingIndex + subString.length();

    if(startingIndex < 0 || endingIndex <0){
    return this;
    }

    public StyledString putLink(String subString, @Nullable final OnSpanClickListener spanClickListener){
    if(getStartEnd(subString)){
    //clickable span with listener
    ClickableSpan clickableSpan = new ClickableSpan() {

    @@ -103,25 +91,63 @@ public void onClick(View widget) {
    }
    }
    };

    fullStringBuilder.setSpan(clickableSpan,startingIndex, endingIndex, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

    }

    return this;
    }


    /**
    * give a substring a color
    * @param subString Substring
    * @param colorRes color resource
    * @return StyledString with color
    */
    public StyledString putColor(String subString, @ColorRes int colorRes){
    if(getStartEnd(subString)){
    int color = ColorUtil.getColor(context, colorRes);
    ForegroundColorSpan foregroundColorSpan = new ForegroundColorSpan(color);
    fullStringBuilder.setSpan(foregroundColorSpan, startingIndex, endingIndex, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
    }
    return this;
    }


    /**
    * show directly in the given textview
    * @param textView TextView
    */
    public StyledString toView(TextView textView){
    textView.setMovementMethod(LinkMovementMethod.getInstance()); //make links clickable
    textView.setText(getStringBuilder(), TextView.BufferType.SPANNABLE);
    return this;
    }

    public SpannableStringBuilder getStringBuilder(){
    return fullStringBuilder;
    }


    /**
    * calculate the beginning and end index of the substring
    * @param subString String
    * @return boolean true if index calculations are correctly done
    */
    private boolean getStartEnd(String subString){
    if(subString.length() > 0 && !subString.trim().equals("")) {
    //for counting start/end indexes
    startingIndex = fullString.indexOf(subString);
    endingIndex = startingIndex + subString.length();

    if(startingIndex < 0 || endingIndex <0){
    return false;
    }

    return true;
    }

    return false;
    }

    }
  2. janvde revised this gist Apr 11, 2016. No changes.
  3. janvde renamed this gist Apr 4, 2016. 1 changed file with 0 additions and 0 deletions.
    File renamed without changes.
  4. janvde created this gist Apr 4, 2016.
    127 changes: 127 additions & 0 deletions StyledString
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,127 @@
    import android.content.Context;
    import android.support.annotation.StringRes;
    import android.support.annotation.StyleRes;
    import android.text.Spannable;
    import android.text.SpannableStringBuilder;
    import android.text.style.ClickableSpan;
    import android.text.style.TextAppearanceSpan;
    import android.view.View;
    import android.widget.TextView;

    /**
    * Created by jan on 01/04/16.
    * enables making a string stylable by giving multiple substrings a style
    * capable of method chaining
    */


    public class StyledString {

    public interface OnSpanClickListener {
    void onSpanClicked();
    }

    private SpannableStringBuilder fullStringBuilder;
    private String fullString;
    private Context context;


    /**
    * constructor for string
    * @param context Context
    * @param fullString full length string
    */
    public StyledString(Context context, String fullString){
    fullStringBuilder = new SpannableStringBuilder(fullString);
    this.fullString = fullString;
    this.context = context;
    }

    /**
    * constructor for string resource
    * @param context Context
    * @param fullStringRes full length string resource
    */
    public StyledString(Context context, @StringRes int fullStringRes){
    String fullString = context.getString(fullStringRes);
    fullStringBuilder = new SpannableStringBuilder(fullString);
    this.fullString = fullString;
    }


    /**
    * give a substring a styling
    * @param subString substring of the fullstring
    * @param textAppearance text style
    * @return Styledstring
    */
    public StyledString put(String subString, @StyleRes int textAppearance){
    if(subString.length() > 0 && !subString.trim().equals("")) {

    //for counting start/end indexes
    int startingIndex = fullString.indexOf(subString);
    int endingIndex = startingIndex + subString.length();

    if(startingIndex < 0 || endingIndex <0){
    return this;
    }

    TextAppearanceSpan textAppearanceSpan = new TextAppearanceSpan(context, textAppearance);
    fullStringBuilder.setSpan(textAppearanceSpan, startingIndex, endingIndex, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
    }

    return this;
    }


    /**
    * give a substring a clickable link
    * add this to textview: textView.setMovementMethod(LinkMovementMethod.getInstance());
    *
    * @param subString to make clickable
    * @param spanClickListener listener to listen for cliks, can be null
    * @return StyledString
    */
    public StyledString putLink(String subString, final OnSpanClickListener spanClickListener){
    if(subString.length() > 0 && !subString.trim().equals("")) {

    //for counting start/end indexes
    int startingIndex = fullString.indexOf(subString);
    int endingIndex = startingIndex + subString.length();

    if(startingIndex < 0 || endingIndex <0){
    return this;
    }

    //clickable span with listener
    ClickableSpan clickableSpan = new ClickableSpan() {

    @Override
    public void onClick(View widget) {
    if (spanClickListener != null) {
    spanClickListener.onSpanClicked();
    }
    }
    };

    fullStringBuilder.setSpan(clickableSpan,startingIndex, endingIndex, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

    }

    return this;
    }


    /**
    * show directly in the given textview
    * @param textView TextView
    */
    public StyledString toView(TextView textView){
    textView.setText(getStringBuilder(), TextView.BufferType.SPANNABLE);
    return this;
    }

    public SpannableStringBuilder getStringBuilder(){
    return fullStringBuilder;
    }
    }