Home » Android » Android circle background becomes oval

Android circle background becomes oval

Posted by: admin April 23, 2020 Leave a comment

Questions:

I want to put a circle background on a textview. The circle becomes oval when its rendered.

My layout XML:

    <TextView
        android:id="@+id/amount_key"
        android:layout_weight="1"
        android:layout_height="match_parent"
        android:layout_width="match_parent"
        android:layout_marginRight="2dp"
        android:gravity="center"
        android:background="@drawable/circle"
        android:layout_marginLeft="20dp"
        android:text="3\ndays"
        android:padding="20dp"
        android:textColor="#ffffff"
        android:textStyle="bold"
        android:textSize="25dp" />


</LinearLayout>

My circle background:

<shape 
    xmlns:android="http://schemas.android.com/apk/res/android"
            android:shape="oval">

            <solid 
               android:color="#79bfea"/>
</shape>
How to&Answers:
  • Change your textView‘s layout_height and layout_width to wrap_content
  • Add size tag inside shape tag as follows
<shape 
xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="oval">> 
<solid android:color="#79bfea" />
<size android:height="25dp"
   android:width="25dp"/>
</shape>

If it is still oval, try increasing the width and height in size tag. It worked for me!

Answer:

You can create your own Drawable which will constrain the radius to the min value between its width and height.

package com.example.android;

import android.graphics.Canvas;
import android.graphics.ColorFilter;
import android.graphics.Paint;
import android.graphics.PixelFormat;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;

public class ColorCircleDrawable extends Drawable {
    private final Paint mPaint;
    private int mRadius = 0;

    public ColorCircleDrawable(final int color) {
        this.mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        this.mPaint.setColor(color);
    }

    @Override
    public void draw(final Canvas canvas) {
        final Rect bounds = getBounds();
        canvas.drawCircle(bounds.centerX(), bounds.centerY(), mRadius, mPaint);
    }

    @Override
    protected void onBoundsChange(final Rect bounds) {
        super.onBoundsChange(bounds);
        mRadius = Math.min(bounds.width(), bounds.height()) / 2;
    }

    @Override
    public void setAlpha(final int alpha) {
        mPaint.setAlpha(alpha);
    }

    @Override
    public void setColorFilter(final ColorFilter cf) {
        mPaint.setColorFilter(cf);
    }

    @Override
    public int getOpacity() {
        return PixelFormat.TRANSLUCENT;
    }
}

then apply to your textView:

textView.setBackground(new ColorCircleDrawable(Color.RED));

Answer:

To get this

enter image description here

I used two LinearLayout inside each other and set parent gravity to CENTER

<LinearLayout
android:layout_width="80dp"
android:layout_height="50dp"
android:baselineAligned="false"
android:gravity="center"
android:orientation="vertical">

<LinearLayout
    android:layout_width="45dp"
    android:layout_height="45dp"
    android:gravity="center"
    android:background="@drawable/oval"
    android:orientation="vertical">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:text="Text"
        android:textSize="12sp" />
</LinearLayout>
</LinearLayout>

and this is oval.xml inside drawable folder

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="oval">
    <solid android:color="#393939" />
    <size
        android:width="40dp"
        android:height="40dp" />
</shape>

without inner LinearLayout you’ll get this

enter image description here

which it’s code is

<LinearLayout
android:layout_width="80dp"
android:layout_height="50dp"
android:baselineAligned="false"
android:gravity="center"
android:background="@drawable/oval"
android:orientation="vertical">

<TextView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_gravity="center"
    android:text="Text"
    android:textSize="12sp" />
</LinearLayout>

Answer:

I extended TextView class to set width as height

public class TextViewSquareShaped extends TextView {


public TextViewSquareShaped(Context context, AttributeSet attrs, int defStyle) {
    super(context, attrs, defStyle);
    init(attrs);
}

public TextViewSquareShaped(Context context, AttributeSet attrs) {
    super(context, attrs);
    init(attrs);

}

public TextViewSquareShaped(Context context) {
    super(context);
    init(null);
}

private void init(AttributeSet attrs) {
}

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    int width = getDefaultSize(getSuggestedMinimumWidth(), widthMeasureSpec);
    setMeasuredDimension(width, width);
    Log.v("measure", "width:" + width + " height:" + width);
 }
}

And then combined with above Sudhasri’s answer, I can show exact circular text view.

So no need to give fixed height and weight.

Answer:

Since you are using match_parent for width and height and setting drawable in background, so it will be oval. To achieve circle you can give same dimensions for width and height. NA dif want full screen then you can width from java code using WindowManager and set the same value in both width and height.

Answer:

try ring instead of oval

<shape 
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="ring" >

    <solid android:color="#79bfea" />
</shape>