Antonio
Antonio

Reputation: 3148

Is there an easy way to strike through text in an app widget?

I was wondering if there is an easy way to strike text within an app widget in Android. In a normal activity, it is pretty easy, using textview flags:

textView.setPaintFlags(textView.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);

But since in an app widget, I can use only remoteviews... I do not know if this is possible

Anyone know something about this?

Thanks!

Upvotes: 164

Views: 128832

Answers (23)

Savai Solanki
Savai Solanki

Reputation: 11

-create a binding adapter class and add this method

@BindingAdapter("strikeThrough")
    @JvmStatic
    fun strikeThrough(textView: MaterialTextView, strikeThrough: Boolean) {
        if (strikeThrough) {
            textView.paintFlags = textView.paintFlags or Paint.STRIKE_THRU_TEXT_FLAG
        } else {
            textView.paintFlags = textView.paintFlags and Paint.STRIKE_THRU_TEXT_FLAG.inv()
        }
    }

on xml u have to set this

        <com.google.android.material.textview.MaterialTextView
            android:id="@+id/txtFormattedFinalPrice"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textColor="@color/text_color_discount"
            android:textSize="@dimen/_8ssp"
            app:strikeThrough="@{true}"
            app:layout_constraintStart_toStartOf="parent"
          />

Upvotes: 1

Firas Shrourou
Firas Shrourou

Reputation: 715

I created this method to use from any where within my app

static String formatSellingPrice(Context ctx, String Original_Price, String Selling_Price, boolean isUnder_Promotion) {
        String Currency_Symbol = ctx.getResources().getString(R.string.Currency_Symbol);

        if (isUnder_Promotion) {
            return String.format("<strike><font color=\"#757575\">%s %s</font></strike> %s %s", Original_Price, Currency_Symbol, Selling_Price, Currency_Symbol);
        } else {
            return Selling_Price + " " + Currency_Symbol;
        }
    }

it can be used if you have multi language and multi currency app

I call it like this:

String formated_SellingPrice = formatSellingPrice(this, Original_Price, Selling_Price, isUnder_Promotion);

then assign like this

tv_Card_Selling_Price.setText(Html.fromHtml(formated_SellingPrice));

Upvotes: 0

artem
artem

Reputation: 16808

Another solution as a Kotlin extension:

var TextView.isStrikeThrough: Boolean
    get() = (paintFlags and Paint.STRIKE_THRU_TEXT_FLAG) == Paint.STRIKE_THRU_TEXT_FLAG
    set(value) {
        paintFlags = if (value) {
            paintFlags or Paint.STRIKE_THRU_TEXT_FLAG
        } else {
            paintFlags and Paint.STRIKE_THRU_TEXT_FLAG.inv()
        }
    }

Upvotes: 0

Juan Martinez
Juan Martinez

Reputation: 121

Kotlin way

averagePrice.paintFlags = Paint.STRIKE_THRU_TEXT_FLAG

Upvotes: 2

Papa Yev
Papa Yev

Reputation: 628

You Can use data binding! In XML layout just do app:strike="@{true}"

@BindingAdapter("strike")
fun bindTextView(view: TextView, strike: Boolean) {
    if (strike) {
        view.paintFlags = view.paintFlags or Paint.STRIKE_THRU_TEXT_FLAG or Paint.ANTI_ALIAS_FLAG
    } else {
        view.paintFlags = 0 or Paint.ANTI_ALIAS_FLAG
    }
}

Upvotes: 1

Mujahid Khan
Mujahid Khan

Reputation: 1834

Kotlin way

val tv = findViewById<View>(R.id.mytext) as TextView
tv.text = "This is strike-through"
tv.paintFlags = tv.paintFlags or Paint.STRIKE_THRU_TEXT_FLAG

Upvotes: 3

d-feverx
d-feverx

Reputation: 1672

Make a drawable file, striking_text.xml

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="false">
        <shape android:shape="line">
            <stroke android:width="1dp" android:color="@android:color/holo_red_dark" />
        </shape>
    </item>
</selector>

layout xml

 <TextView
            ....
            ....
            android:background="@drawable/striking_text"
            android:foreground="@drawable/striking_text"
            android:text="69$"
           />

If your min SDK below API level 23 just use the background or just put the background and foreground in the Textview then the android studio will show an error that says create a layout file for API >23 after that remove the android:foreground="@drawable/stricking_text" from the main layout

Output look like this: enter image description here

Upvotes: 13

Akshay More
Akshay More

Reputation: 436

For Lollipop and above. create a drawable

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="false">
        <shape android:shape="line">
            <stroke android:width="1dp"
                android:color="@color/onePlusRed" />
        </shape>
    </item>
</selector>

and use it as foreground.
android:foreground="@drawable/strike_through"

Upvotes: 2

Ilya Gazman
Ilya Gazman

Reputation: 32281

Android resources have pretty good HTML markup support
The below HTML elements are supported:

Bold: <b>, <em>
Italic: <i>, <cite>, <dfn>
25% larger text: <big>
20% smaller text: <small>
Setting font properties: <font face=”font_family“ color=”hex_color”>. Examples of possible font families include monospace, serif, and sans_serif.
Setting a monospace font family: <tt>
Strikethrough: <s>, <strike>, <del>
Underline: <u>
Superscript: <sup>
Subscript: <sub>
Bullet points: <ul>, <li>
Line breaks: <br>
Division: <div>
CSS style: <span style=”color|background_color|text-decoration”>
Paragraphs: <p dir=”rtl | ltr” style=”…”>

Note however that it's not rendered in android studio layouts preview. Last tested on Android Studio 3.3.1

For example, the Strikethrough will look like that:

<string name="cost"><strike>$10</strike> $5 a month</string>

Upvotes: 2

Michael
Michael

Reputation: 9904

Here is an extension for all you Kotlin folks

fun TextView.showStrikeThrough(show: Boolean) {
    paintFlags =
            if (show) paintFlags or Paint.STRIKE_THRU_TEXT_FLAG
            else paintFlags and Paint.STRIKE_THRU_TEXT_FLAG.inv()
}

Usage

textView.showStrikeThrough(true)

Limitation

Strikethroughs can only be the same color as the text

(i.e. Red text and blue strikethrough is not possible)

Upvotes: 26

Abhishek c
Abhishek c

Reputation: 549

try this code

textview.setText((Html.fromHtml("<strike>hello world!</strike>")));

Upvotes: 6

Ram Koti
Ram Koti

Reputation: 2211

I know, I am answering an old question, it might be helpful for someone else, for striking out a particular portion of TextView programmatically.

TextView textView = (TextView) findViewById(R.id.textView);
textView.setText("Text need to be set here", TextView.BufferType.SPANNABLE);
Spannable spannable = (Spannable) textView.getText();
spannable.setSpan(new StrikethroughSpan(), 5, 8, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);

So, in this example code, 5 is starting position and 8 is ending position of text need to be stricken out, so after running this code we can get the text "need" with striked out. Hope it will helpful for someone else.

Upvotes: -1

Milos Simic Simo
Milos Simic Simo

Reputation: 169

I tried few options but, this works best for me:

String text = "<strike><font color=\'#757575\'>Some text</font></strike>";
textview.setText(Html.fromHtml(text));

cheers

Upvotes: 0

pavel
pavel

Reputation: 1701

For doing this you can use this

 title.setPaintFlags(title.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);

and for remove you can use this

 title.setPaintFlags(title.getPaintFlags() & (~Paint.STRIKE_THRU_TEXT_FLAG));

Upvotes: 41

Briliant Fay
Briliant Fay

Reputation: 45

you add in :

TextView variableTv = (TextView) findViewById(R.id.yourText);

you set/add in You variable :

variableTv.setText("It's Text use Style Strike");

and then add .setPaintFlags in variableTv :

variableTv.setPaintFlags(variableTv.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);

Upvotes: 0

ChandraMouli Poreddy
ChandraMouli Poreddy

Reputation: 420

Add the line below:-

TextView tv=(TextView) v.findViewById(android.R.id.text1);
tv.setPaintFlags(tv.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);

use your reference instead of "tv"

Upvotes: 8

ohhorob
ohhorob

Reputation: 11805

2015 Update: Folks, this is for very old versions of Android. See other answers for modern solutions!


To strike through the entire text view, you can use a specific background image to simulate the strikethrough effect:

android:background="@drawable/bg_strikethrough"

Where the bg_strikethrough drawable is a 9-patch that keeps a solid line through the middle, growing either side, with however much padding you think is reasonable. I've used one like this:

alt text

(enlarged for clarity.. 1300% !)

alt text

That is my HDPI version, so save it (the first one https://i.sstatic.net/nt6BK.png) as res/drawable-hdpi/bg_strikethrough.9.png and the configuration will work as so:

alt text

Upvotes: 61

user3768270
user3768270

Reputation: 99

For multiline TextView you should use android.text.style.CharacterStyle like this:

SpannableString spannable = new SpannableString(text);
spannable.setSpan(new StrikethroughSpan(), 0, text.length(), Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
remoteViews.setTextViewText(R.id.itemText, spannable);

Upvotes: 9

Ignacio Alorre
Ignacio Alorre

Reputation: 7615

It is really easy if you are using strings:

<string name="line"> Not crossed <strike> crossed </strike> </string>

And then just:

<TextView 
        ...
         android:text="@string/line"
 />

Upvotes: 12

BoD
BoD

Reputation: 11045

Another way to do it programmatically which looks a bit less like a hack than the Paint way:

Instead of doing:

tv.setText(s);

do:

private static final StrikethroughSpan STRIKE_THROUGH_SPAN = new StrikethroughSpan();
...
tv.setText(s, TextView.BufferType.SPANNABLE);
Spannable spannable = (Spannable) tv.getText();
spannable.setSpan(STRIKE_THROUGH_SPAN, 0, s.length(), Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);

Upvotes: 88

agirardello
agirardello

Reputation: 2915

You can use this:

remoteviews.setInt(R.id.YourTextView, "setPaintFlags", Paint.STRIKE_THRU_TEXT_FLAG | Paint.ANTI_ALIAS_FLAG);

Of course you can also add other flags from the android.graphics.Paint class.

Upvotes: 76

ruhalde
ruhalde

Reputation: 3551

To do it programatically in a textview, untested in other views >>

TextView tv = (TextView) findViewById(R.id.mytext);
tv.setText("This is strike-thru");
tv.setPaintFlags(tv.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);

Upvotes: 217

Blrfl
Blrfl

Reputation: 7003

I've done this on a regular (local) TextView, and it should work on the remote variety since the docs list the method as equivalent between the two:

remote_text_view.setText(Html.fromHtml("This is <del>crossed off</del>."));

Upvotes: -1

Related Questions