I tried to draw a custom linear layout, But the problem I faced is I am not getting the round corner for the linear layout
public class RoundLinearLayout extends LinearLayout {
private float radius;
private Path path = new Path();
private RectF rect = new RectF();
public RoundLinearLayout(Context context)
{
super(context);
radius = 20;
// setWillNotDraw(false);
}
public RoundLinearLayout(Context context, AttributeSet attrs) {
super(context, attrs);
// init(context);
}
public RoundLinearLayout(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
// init(context);
}
#Override
protected void onDraw(Canvas canvas) {
path.reset();
rect.set(0, 0, canvas.getWidth(), canvas.getHeight());
path.addRoundRect(rect, radius, radius, Path.Direction.CCW);
// Add 1px border RED here ?
path.close();
canvas.clipPath(path);
}
}
I really donno what went wrong.. Some please help me to sort this out.
I will suggest you to use simple CardView
use compile dependency
compile 'com.android.support:cardview-v7:21.0.+'
Example
<android.support.v7.widget.CardView
xmlns:card_view="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<LinearLayout
.....
your other child layout goes here
</LinearLayout>
</android.support.v7.widget.CardView>
Use below xml in Drawables.
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="#FFFFFF" />
<stroke
android:width="2dp"
android:color="#000" />
<padding
android:bottom="1dp"
android:left="1dp"
android:right="1dp"
android:top="1dp" />
<corners
android:bottomLeftRadius="8dp"
android:bottomRightRadius="8dp"
android:radius="8dp"
android:topLeftRadius="8dp"
android:topRightRadius="8dp" />
</shape>
and set it as a Background of your LinearLayout.
You can choose your color and set background to your linear layout.
<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<corners android:radius="4dp" />
<solid android:color="#80000000" />
</shape>
Related
I'm looking for do a button like this preview :
I tried to do this with a button but my problem is that to put the border and the image I use android: background and I can not put the image and the border at the same time :/
Another problem for which I did not know how is a border to the text (which is simply the text of the button).
I wonder if I'm going in the wrong direction. I saw that there were button images but I'm not sure it suits me. Would there be a way to put a layout to a button?
<Button
android:id="#+id/mainButton1"
style="#style/Widget.AppCompat.Button.ButtonBar.AlertDialog"
android:layout_width="150"
android:layout_height="150"
android:background="#drawable/ic_add_circle_green_500_48dp"
android:drawable="#drawable/mainButton" <-- or android:drawable="#drawable/image" how for put the both ? -->
android:text="Text"
/>
mainButton.xml
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<gradient android:startColor="#FFFFFF"
android:endColor="#00FF00"
android:angle="270" />
<corners android:radius="3dp" />
<stroke android:width="5px" android:color="#000000" />
</shape>
i have found many answers on Stackoverflow but the link to tutos was dead ...
You can create your custom View with desired background and ImageView,TextView inside. Then set ClickListener to it.
If you want background behind TextView you can use SpannableString or just create XML drawable and set it as TextView background.
Here what i've done:
Button class:
public class CustomButton extends LinearLayout {
public CustomButton(Context context) {
super(context);
inflateLayout(context);
}
public CustomButton(Context context, #Nullable AttributeSet attrs) {
super(context, attrs);
inflateLayout(context);
}
public CustomButton(Context context, #Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
inflateLayout(context);
}
#TargetApi(Build.VERSION_CODES.LOLLIPOP)
public CustomButton(Context context, #Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
inflateLayout(context);
}
private void inflateLayout(Context context) {
inflate(context, R.layout.custom_button, this);
}
#Override
protected void onFinishInflate() {
super.onFinishInflate();
TextView textView = findViewById(R.id.textView);
makeSpannable(textView);
}
private void makeSpannable(TextView textView) {
Spannable spannable = new SpannableString(textView.getText());
spannable.setSpan(new BackgroundColorSpan(0xFFFF0021), 0, textView.getText().length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
textView.setText(spannable);
invalidate();
}
}
layout for CustomButton:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_gravity="center_horizontal"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:orientation="vertical"
android:background="#drawable/background"
android:padding="16dp">
<ImageView
android:id="#+id/imageView"
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:src="#mipmap/ic_launcher" />
<TextView
android:id="#+id/textView"
android:gravity="center_horizontal"
android:layout_height="wrap_content"
android:layout_marginTop="16dp"
android:layout_width="match_parent"
android:text="CLICK ME!"
android:textSize="16dp" />
</LinearLayout>
background for button:
<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#FFFFFF"/>
<stroke android:width="3dp" android:color="#00FFFF" />
<corners android:radius="10dp"/>
<padding android:left="0dp" android:top="0dp" android:right="0dp" android:bottom="0dp" />
</shape>
What I've got:
I created an Android gradient drawable where the top and bottom are black and the center is transparent:
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<gradient
android:startColor="#android:color/black"
android:centerColor="#android:color/transparent"
android:endColor="#android:color/black"
android:angle="90"/>
</shape>
The rendered gradient looks like this:
As you can see, the black parts spread to most of the screen. I want the black to show only on a small portion of the top and bottom. Is there a way I can make the transparent center larger, or make the top and bottom black stripes smaller?
I tried playing around with some of the other XML attributes mentioned in the linked GradientDrawable documentation, yet none of them seem to make and difference.
For an XML only solution, you can create a layer-list with two separate gradient objects.
The following code creates two overlapping gradient objects and uses centerY with centerColor to offset the black section. Here, the centerY attributes are set to 0.9 and 0.1, so the black color is restricted to the top and bottom 10% of the view height.
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<shape>
<gradient
android:angle="90"
android:centerColor="#android:color/transparent"
android:centerY="0.9"
android:endColor="#android:color/black"
android:startColor="#android:color/transparent" />
</shape>
</item>
<item>
<shape>
<gradient
android:angle="90"
android:centerColor="#android:color/transparent"
android:centerY="0.1"
android:endColor="#android:color/transparent"
android:startColor="#android:color/black" />
</shape>
</item>
</layer-list>
For API level 23 or higher, the following solution will also work, using android:height. This solution can work even if you don't know the total height of your view, as long as you know how large you want the gradient to be.
This code creates two separate gradients, each with a height of 60sp, and then uses android:gravity to float the gradients to the top and bottom of the view.
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:height="60sp"
android:gravity="top">
<shape android:shape="rectangle">
<gradient
android:angle="90"
android:endColor="#android:color/black"
android:startColor="#android:color/transparent" />
</shape>
</item>
<item
android:height="65sp"
android:gravity="bottom">
<shape android:shape="rectangle">
<gradient
android:angle="90"
android:endColor="#android:color/transparent"
android:startColor="#android:color/black" />
</shape>
</item>
</layer-list>
Thank you #Luksprog for the code help, and #thenaoh for the start of the idea.
The above solutions work and it is nice that they are pure XML. If your gradient is showing with stripes, you may want to try a programmatic solution, like shown in #lelloman's answer, to create a smoother gradient.
Here is how it could be done with a custom Drawable. You can tune the LinearGradient as you want, and then set it as the view's background with view.setBackground(new CustomDrawable());.
public class CustomDrawable extends Drawable {
private Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
private int[] colors;
private float[] positions;
public CustomDrawable() {
paint.setStyle(Paint.Style.FILL);
this.colors = new int[]{0xff000000, 0xffaaaaaa, 0xffffffff, 0xffaaaaaa, 0xff000000};
this.positions = new float[]{.0f, .2f, .5f, .8f, 1.f};
}
#Override
public void setBounds(int left, int top, int right, int bottom) {
super.setBounds(left, top, right, bottom);
LinearGradient linearGradient = new LinearGradient(left, top,left, bottom, colors, positions, Shader.TileMode.CLAMP);
paint.setShader(linearGradient);
}
#Override
public void draw(#NonNull Canvas canvas) {
canvas.drawRect(getBounds(), paint);
}
#Override
public void setAlpha(#IntRange(from = 0, to = 255) int alpha) {
paint.setAlpha(alpha);
}
#Override
public void setColorFilter(#Nullable ColorFilter colorFilter) {
paint.setColorFilter(colorFilter);
}
#Override
public int getOpacity() {
return PixelFormat.TRANSPARENT;
}
}
There is a solution, assuming that you know in advance the height of your view (let's say here 60dp):
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:bottom="40dp">
<shape android:shape="rectangle">
<gradient
android:type="linear"
android:angle="90"
android:startColor="#FFFFFF"
android:endColor="#000000"/>
</shape>
</item>
<item
android:top="20dp"
android:bottom="20dp"
android:gravity="center_vertical">
<shape android:shape="rectangle">
<solid android:color="#FFFFFF"/>
</shape>
</item>
<item
android:top="40dp"
android:gravity="bottom">
<shape android:shape="rectangle">
<gradient
android:type="linear"
android:angle="90"
android:startColor="#000000"
android:endColor="#FFFFFF"/>
</shape>
</item>
</layer-list>
But if you don't know the height in advance, another solution would be to make your own custom view, like this:
public class MyView extends ImageView
{
private Paint paint = null;
public MyView(Context context, AttributeSet attrs)
{
super(context, attrs);
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
}
#Override
protected void onDraw(Canvas canvas)
{
super.onDraw(canvas);
paint.setShader(getLinearGradient(0, getHeight()));
canvas.drawPaint(paint);
}
private LinearGradient getLinearGradient(float y0, float y1)
{
// colors :
int[] listeColors = new int[3];
listeColors[0] = 0xFF000000;
listeColors[1] = 0xFFFFFFFF;
listeColors[2] = 0xFFFFFFFF;
// positions :
float[] listPositions = new float[3];
listPositions[0] = 0;
listPositions[1] = 0.25F;
listPositions[2] = 1;
// gradient :
return new LinearGradient(0, y0, 0, y0 + (y1 - y0) / 2, listeColors, listPositions, Shader.TileMode.MIRROR);
}
}
Hope it helps.
I am trying to make parallelogram background for my textview but it is not displaying properly...it display following output
<layer-list >
<item>
<rotate
android:fromDegrees="10"
android:toDegrees="10"
android:pivotX="-40%"
android:pivotY="87%" >
<shape
android:shape="rectangle" >
<stroke android:color="#000000" android:width="10dp"/>
</shape>
</rotate>
</item>
</layer-list>
i need output like this........
As alternative to #mmlooloo's answer, whom a credit goes to, I suggest a xml-drawable solution (since you haven't emphasized exactly what kind of solution you're looking for). In the example below I used a general View, however you can use any other.
Here is the View
<View
android:layout_width="100dp"
android:layout_height="40dp"
android:layout_centerInParent="true"
android:background="#drawable/shape" />
and shape.xml itself
<?xml version="1.0" encoding="UTF-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<!-- Colored rectangle-->
<item>
<shape android:shape="rectangle">
<size
android:width="100dp"
android:height="40dp" />
<solid android:color="#13a89e" />
</shape>
</item>
<!-- This rectangle for the left side -->
<!-- Its color should be the same as layout's background -->
<item
android:right="100dp"
android:left="-100dp"
android:top="-100dp"
android:bottom="-100dp">
<rotate
android:fromDegrees="45">
<shape android:shape="rectangle">
<solid android:color="#ffffff" />
</shape>
</rotate>
</item>
<!-- This rectangle for the right side -->
<!-- Their color should be the same as layout's background -->
<item
android:right="-100dp"
android:left="100dp"
android:top="-100dp"
android:bottom="-100dp">
<rotate
android:fromDegrees="45">
<shape android:shape="rectangle">
<solid android:color="#ffffff" />
</shape>
</rotate>
</item>
</layer-list>
Here is how it looks like:
you can achieve it by creating custom Textview like this:
public class ParallogramTextView extends TextView {
Paint mBoarderPaint;
Paint mInnerPaint;
public ParallogramTextView(Context context) {
super(context);
init();
}
public ParallogramTextView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
init();
}
public ParallogramTextView(Context context, AttributeSet attrs) {
super(context, attrs);
init();
}
private void init() {
mBoarderPaint = new Paint();
mBoarderPaint.setAntiAlias(true);
mBoarderPaint.setColor(Color.BLACK);
mBoarderPaint.setStyle(Paint.Style.STROKE);
mBoarderPaint.setStrokeWidth(6);
mInnerPaint = new Paint();
mInnerPaint.setAntiAlias(true);
mInnerPaint.setColor(Color.parseColor("#13a89e"));
mInnerPaint.setStyle(Paint.Style.FILL);
mInnerPaint.setStrokeJoin(Paint.Join.ROUND);
}
#Override
public void draw(Canvas canvas) {
super.draw(canvas);
Path path = new Path();
path.moveTo(getWidth(),0);
path.lineTo(getWidth()/2, 0);
path.lineTo(0, getHeight());
path.lineTo(getWidth()/2,getHeight());
path.lineTo(getWidth(), 0);
canvas.drawPath(path, mInnerPaint);
canvas.drawPath(path, mBoarderPaint);
}
}
and in the layout file use it like below:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center">
<com.example.ParallogramTextView
android:id = "#+id/result"
android:layout_width="500dp"
android:layout_height="500dp"
android:layout_centerInParent="true"
android:gravity="center"
android:layout_margin="32dp" />
</RelativeLayout>
the result is:
<item
android:bottom="-25dp"
android:top="-25dp"
android:left="25dp"
android:right="25dp">
<rotate android:fromDegrees="20">
<shape android:shape="rectangle">
<size
android:width="50dp"
android:height="100dp"/>
<solid android:color="#13a8de"/>
</shape>
</rotate>
</item>
This one works on alle backgrounds not just white like in the example above
Are you referring to the navigation menu? If so, you can use this code to make a parallelogram:
ul#nav li a {
display: inline-block;
text-decoration:none;
padding:4px 10px;
border-radius:3px;
transform: skew(-10deg);
-o-transform: skew(-10deg);
-moz-transform: skew(-10deg);
-webkit-transform: skew(-10deg);
color:#000000;
}
ul#nav li a span {
display: inline-block;
transform: skew(10deg);
-o-transform: skew(10deg);
-moz-transform: skew(10deg);
-webkit-transform: skew(10deg);
}
You can also check the HTML and CSS version in codepen.
Hope this helps.
I have developed an rss application. I want the ListView which contains the titles and images to have the images with rounded corners. I have taken a sample code online, but the problem is that the images are still rectangular. The weird part is that I have a sliding menu, when toggled it pushes the rss ListView away, while it's being pushed the images have round corners! when they stop their pushing animation the become rectangular again. It's a pretty weird problem for me so any help?
Rounded Image class:
public class RoundedImageView extends ImageView
{
private float radius = 20.0f;
public RoundedImageView(Context context)
{
super(context);
}
public RoundedImageView(Context context,AttributeSet attrs)
{
super(context,attrs);
}
public RoundedImageView(Context context,AttributeSet attrs,int defStyle)
{
super(context,attrs,defStyle);
}
#SuppressLint("DrawAllocation")
#Override
protected void onDraw(Canvas canvas)
{
Path clipPath = new Path();
RectF rect = new RectF(0,0,getWidth(), getHeight());
clipPath.addRoundRect(rect, radius, radius, Path.Direction.CW);
canvas.clipPath(clipPath);
super.onDraw(canvas);
}
}
Try this way: create rounded_corner.xml file into drawable\rounded_corner.xml
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="#101010" />
<stroke
android:width="1dp"
android:color="#808080" />
<corners android:radius="15dp" />
And set as Background to your ImageView like
android:background="#drawable\rounded_corner"
And also set your RSS image to ImageView as a Src or a Bitmap like:
imageview.setBitmap(yourrssimage);
use rounded corner image or create xml and set as background image on imageview.
Create one XML like below in your drawable folder.
button_back.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:state_enabled="false"
android:drawable="#color/grey">
<shape>
<solid
android:color="#ef4444" />
<stroke
android:width="1dp"
android:color="#992f2f" />
<corners
android:radius="16dp" />
</shape>
</item>
and then apply to your button like this.
<Button
android:text="#string/press_me"
android:layout_margin="12dp"
android:layout_width="fill_parent"
android:layout_height="30dp"
android:background="#drawable/button_back"
/>
Create a stroke and list it as your imageview background
<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#android:color/transparent"/>
<stroke android:width="5dip" android:color="#android:color/transparent" />
<corners android:radius="5dip"/>
<padding android:left="0dip" android:top="0dip" android:right="0dip" android:bottom="0dip" />
</shape>
And in your imageview xml
android:background="#drawable/your_stroke_xml"
How can we create ballon drawable shape as below. where we can change the color of it dynamically.
Here it is XML for triangle and rectangle. save it inside drawable folder.
triangle.xml
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item >
<rotate
android:fromDegrees="45"
android:toDegrees="45"
android:pivotX="-40%"
android:pivotY="87%" >
<shape
android:shape="rectangle" >
<stroke android:color="#android:color/transparent" android:width="10dp"/>
<solid
android:color="#000000" />
</shape>
</rotate>
</item>
</layer-list>
rectangle.xml
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item>
<shape android:shape="rectangle">
<solid android:color="#B2E3FA" />
</shape>
</item>
</layer-list>
and layout for shape you require.
<RelativeLayout
android:id="#+id/rlv1"
android:layout_width="150dp"
android:layout_height="50dp"
android:background="#drawable/rectangle" />
<RelativeLayout
android:id="#+id/rlv2"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_below="#+id/rlv1"
android:background="#drawable/triangle"
android:rotation="180" />
set margin according you required.
Source
If you want a border for your layout
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/linear_root"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
>
<TextView
android:id="#+id/text_message"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:background="#drawable/bg_rectangle"
android:layout_marginLeft="20dp"
android:layout_marginRight="20dp"
android:layout_marginTop="20dp"
android:padding="8dp"
android:text="Abc"
/>
<ImageView
android:id="#+id/image_arrow"
android:layout_marginTop="-1.5dp"
android:layout_width="16dp"
android:layout_height="16dp"
android:layout_gravity="center_horizontal"
android:background="#drawable/icon_arrow_down"
/>
</LinearLayout>
bg_rectangle
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="#eaeaea" />
<stroke
android:width="1dp"
android:color="#f00" />
<corners android:radius="8dp" />
</shape>
icon_arrow_down, or you can create triangle by vector like here
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<rotate
android:fromDegrees="45"
android:pivotX="135%"
android:pivotY="15%"
android:toDegrees="45"
>
<shape android:shape="rectangle">
<solid android:color="#eaeaea"/>
<stroke
android:width="1dp"
android:color="#f00" />
</shape>
</rotate>
</item>
</layer-list>
The clean and right way to do this whilst keeping it dynamic is to extend the View class.
Then in the onDraw you would do something like this:
#Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
drawBackground(canvas);
}
private void drawBackground(Canvas canvas) {
int width = (int) mWidth;
int height = (int) mHeight;
Point a = new Point(0, 0);
Point b = new Point(width, 0);
Point c = new Point(width, height - mPointHeight);//mPointedHeight is the length of the triangle... in this case we have it dynamic and can be changed.
Point d = new Point((width/2)+(mPointedHeight/2), height - mPointHeight);
Point e = new Point((width/2), height);// this is the sharp point of the triangle
Point f = new Point((width/2)-(mPointedHeight/2), height - mPointHeight);
Point g = new Point(0, height - mPointHeight);
Path path = new Path();
path.moveTo(a.x, a.y);
path.lineTo(b.x, b.y);
path.lineTo(c.x, c.y);
path.lineTo(d.x, d.y);
path.lineTo(e.x, e.y);
path.lineTo(f.x, f.y);
path.lineTo(g.x, g.y);
canvas.drawPath(path, mPointedBackgroundPaint);// mPointedBackgroundPaint is whatever color you want as the fill.
}
There you go, no unnecessary layering or code that isn't dynamic or clean. You could also add the text in the box too.
Use a triangle image and a rectangular image and mathematically align them in the above mentioned format. Use color filtering to dynamically change its color.
You can even draw them on a custom view, using vector graphics, using custom colors, and that would be another way of solving this problem.
Create custom view and draw traingle with canvas
package com.example.dickbutt;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;
import android.util.AttributeSet;
import android.view.View;
public class TriangleShapeView extends View {
public int colorCode = Color.MAGENTA;
public int getColorCode() {
return colorCode;
}
public void setColorCode(int colorCode) {
this.colorCode = colorCode;
}
public TriangleShapeView(Context context) {
super(context);
}
public TriangleShapeView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public TriangleShapeView(Context context, AttributeSet attrs) {
super(context, attrs);
}
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
int w = getWidth() / 2;
int h = getHeight() / 2;
Path path = new Path();
path.moveTo(0, 0);
path.lineTo(w, 2 * h);
path.lineTo(2 * w, 0);
path.lineTo(0, 0);
path.close();
Paint p = new Paint();
p.setColor(colorCode);
p.setAntiAlias(true);
canvas.drawPath(path, p);
}
}
Result
Usage
<TextView
android:id="#+id/progress_value"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:background="#android:color/holo_purple"
android:gravity="center_horizontal"
android:text="200,0000000"
android:textColor="#fff" />
<com.example.dickbutt.TriangleShapeView
android:id="#+id/textView1"
android:layout_width="10dp"
android:layout_height="20dp"
android:layout_below="#+id/progress_value"
android:layout_centerHorizontal="true"
android:background="#drawable/rectangle"
android:gravity="center_horizontal"
android:textSize="10sp" />
Advantages
Change shape according to width and height of view .
Highly customization possible.
Look cleaner
Use Canvas in onDraw method inside custom View class.
Other way is to use Path class.
First you can create one xml inside drawable folder
That xml will be responsible for the border color of rectangle shape
You can create such border shape with below code
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<shape android:shape="rectangle">
<solid android:color="#B2E3FA" />
</shape>
</item>
<item android:left="5dp" android:bottom="5dp" android:top="5dp" >
<shape android:shape="rectangle">
<solid android:color="#D8D8D8" />
</shape>
</item>
</layer-list>
well this will create a required border to rectangle shape, you need to assign background of that rectangle shape with this drawable like this
android:background="#drawable/bg"
where bg is xml file name which has been saved on drawable folder
After that you need to put that triangle exactly below to rectangle object.
I hope you understood my logic