ImageView 只有一个圆角
Posted
技术标签:
【中文标题】ImageView 只有一个圆角【英文标题】:ImageView with only one rounded corner 【发布时间】:2020-04-02 13:22:27 【问题描述】:我正在尝试制作ImageView
的一个圆角,如下图所示,但带有右下角。尝试使用背景形状,但它根本不起作用。 Glide 加载的所有图像。我应该使用ViewOutlineProvider
之类的东西吗?有没有一种有效的方法来做到这一点?谢谢!
<shape xmlns:android="http://schemas.android.com/apk/res/android" >
<corners
android:radius="2dp"
android:bottomRightRadius="20dp"
android:bottomLeftRadius="0dp"
android:topLeftRadius="0dp"
android:topRightRadius="0dp"/>
</shape>
【问题讨论】:
这里是可能对你有用的库:github.com/pungrue26/SelectableRoundedImageView 你能发布一张视图的图片吗,它是如何使用你添加的当前代码寻找你的?因为相同的代码给了我你想要的底部圆角。还要发布要应用形状的 ImageView 的代码 【参考方案1】:Material Components library从1.2.0-alpha03
版本开始引入了ShapeableImageView
。
只需使用类似的东西:
<com.google.android.material.imageview.ShapeableImageView
android:id="@+id/image_view"
android:scaleType="centerInside"
android:adjustViewBounds="true"
../>
然后在您的代码中,您可以将ShapeAppearanceModel
应用于:
ShapeableImageView imageView = findViewById(R.id.image_view);
float radius = getResources().getDimension(R.dimen.default_corner_radius);
imageView.setShapeAppearanceModel(imageView.getShapeAppearanceModel()
.toBuilder()
.setTopRightCorner(CornerFamily.ROUNDED,radius)
.build());
你也可以在xml中应用shapeAppearanceOverlay
参数:
<com.google.android.material.imageview.ShapeableImageView
app:shapeAppearanceOverlay="@style/customRroundedImageView"
app:srcCompat="@drawable/ic_image" />
与:
<style name="customRoundedImageView" parent="">
<item name="cornerFamily">rounded</item>
<item name="cornerSize">0dp</item>
<item name="cornerSizeTopRight">8dp</item>
</style>
使用 jetpack compose,您可以使用 RoundedCornerShape
应用 clip
修饰符:
Image(painterResource(id = R.drawable.xxx),
contentDescription = "xxxx",
contentScale = ContentScale.Crop,
modifier = Modifier
.size(xx.dp,xx.dp)
.clip(RoundedCornerShape(topStart = 12.dp)),
)
【讨论】:
是否仍然不支持在ShapeableImageView
上通过 XML(直接在视图上或通过样式/主题)自定义 shapeAppearance
和/或 shapeAppearanceOverlay
?
@Richard 是的。例如,您可以在 xml 布局中使用:app:shapeAppearance="?attr/shapeAppearanceMediumComponent"
。
谢谢,它成功了 ;-) 虽然它在 Android Studio 布局预览中没有正确显示。运行时,ShapeableImageView
正确显示(带有圆形边缘)。在预览时,它显示一个矩形。这是一个错误吗?
此功能现在在 1.2.0 中稳定【参考方案2】:
此外,如果您想摆脱在“.java”文件中编写代码。然后你可以像下面这样定义 style 并将其添加到你的ShapeableImageView
:
<com.google.android.material.imageview.ShapeableImageView
android:layout_
android:layout_
android:src="@drawable/ex_image"
app:shapeAppearanceOverlay="@style/roundedImageView"
/>
然后:
<style name="roundedImageView" parent="">
<item name="cornerFamilyTopRight">rounded</item>
<item name="cornerSizeTopRight">30dp</item>
</style>
【讨论】:
【参考方案3】:这是您的主要布局文件,它使用自定义可绘制“round_one.xml”文件。只需复制并粘贴此代码。 它有望满足您的要求。
<?xml version="1.0" encoding="utf-8"?>
<androidx.cardview.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:elevation="@dimen/_10sdp"
android:background="@color/white"
android:orientation="vertical" android:layout_
android:layout_>
<LinearLayout
android:id="@+id/linearLayout2"
android:layout_
android:layout_
android:background="@drawable/round_one"
android:orientation="vertical"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">
<ImageView
android:layout_
android:layout_
android:layout_gravity="center"
android:scaleType="fitXY"
android:src="@android:drawable/ic_menu_day" />
<TextView
android:id="@+id/textView22"
android:layout_
android:layout_
android:layout_marginStart="16dp"
android:layout_marginTop="16dp"
android:layout_marginEnd="8dp"
android:text="title goes here" />
<TextView
android:layout_
android:layout_
android:layout_marginStart="16dp"
android:layout_marginTop="8dp"
android:layout_marginBottom="8dp"
android:text="Secondary text"
/>
</LinearLayout>
</androidx.cardview.widget.CardView>
round_one.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="@color/gray" />
<corners android:topRightRadius="50dp" />
</shape>
【讨论】:
【参考方案4】:要只圆 imageview 的一个角,请按照以下步骤和代码:
将以下文件添加到您的项目RoundCornerImageView.java
package com.skd.stackdemo;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.res.ColorStateList;
import android.content.res.Resources;
import android.content.res.TypedArray;
import android.graphics.Bitmap;
import android.graphics.BitmapShader;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.ColorFilter;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PixelFormat;
import android.graphics.Rect;
import android.graphics.RectF;
import android.graphics.Shader;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.graphics.drawable.LayerDrawable;
import android.net.Uri;
import android.util.AttributeSet;
import android.util.Log;
import android.widget.ImageView;
public class RoundCornerImageView extends ImageView
public static final String TAG = "RoundCornerImageView";
private int mResource = 0;
private static final ScaleType[] sScaleTypeArray =
ScaleType.MATRIX,
ScaleType.FIT_XY,
ScaleType.FIT_START,
ScaleType.FIT_CENTER,
ScaleType.FIT_END,
ScaleType.CENTER,
ScaleType.CENTER_CROP,
ScaleType.CENTER_INSIDE
;
// Set default scale type to FIT_CENTER, which is default scale type of
// original ImageView.
private ScaleType mScaleType = ScaleType.FIT_CENTER;
private float mLeftTopCornerRadius = 0.0f;
private float mRightTopCornerRadius = 0.0f;
private float mLeftBottomCornerRadius = 0.0f;
private float mRightBottomCornerRadius = 0.0f;
private float mBorderWidth = 0.0f;
private static final int DEFAULT_BORDER_COLOR = Color.BLACK;
private ColorStateList mBorderColor = ColorStateList.valueOf(DEFAULT_BORDER_COLOR);
private boolean isOval = false;
private Drawable mDrawable;
private float[] mRadii = new float[] 0, 0, 0, 0, 0, 0, 0, 0 ;
public RoundCornerImageView(Context context)
super(context);
public RoundCornerImageView(Context context, AttributeSet attrs)
this(context, attrs, 0);
public RoundCornerImageView(Context context, AttributeSet attrs, int defStyle)
super(context, attrs, defStyle);
TypedArray a = context.obtainStyledAttributes(attrs,
R.styleable.SelectableRoundedImageView, defStyle, 0);
final int index = a.getInt(R.styleable.SelectableRoundedImageView_android_scaleType, -1);
if (index >= 0)
setScaleType(sScaleTypeArray[index]);
mLeftTopCornerRadius = a.getDimensionPixelSize(
R.styleable.SelectableRoundedImageView_sriv_left_top_corner_radius, 0);
mRightTopCornerRadius = a.getDimensionPixelSize(
R.styleable.SelectableRoundedImageView_sriv_right_top_corner_radius, 0);
mLeftBottomCornerRadius = a.getDimensionPixelSize(
R.styleable.SelectableRoundedImageView_sriv_left_bottom_corner_radius, 0);
mRightBottomCornerRadius = a.getDimensionPixelSize(
R.styleable.SelectableRoundedImageView_sriv_right_bottom_corner_radius, 0);
if (mLeftTopCornerRadius < 0.0f || mRightTopCornerRadius < 0.0f
|| mLeftBottomCornerRadius < 0.0f || mRightBottomCornerRadius < 0.0f)
throw new IllegalArgumentException("radius values cannot be negative.");
mRadii = new float[]
mLeftTopCornerRadius, mLeftTopCornerRadius,
mRightTopCornerRadius, mRightTopCornerRadius,
mRightBottomCornerRadius, mRightBottomCornerRadius,
mLeftBottomCornerRadius, mLeftBottomCornerRadius ;
mBorderWidth = a.getDimensionPixelSize(
R.styleable.SelectableRoundedImageView_sriv_border_width, 0);
if (mBorderWidth < 0)
throw new IllegalArgumentException("border width cannot be negative.");
mBorderColor = a
.getColorStateList(R.styleable.SelectableRoundedImageView_sriv_border_color);
if (mBorderColor == null)
mBorderColor = ColorStateList.valueOf(DEFAULT_BORDER_COLOR);
isOval = a.getBoolean(R.styleable.SelectableRoundedImageView_sriv_oval, false);
a.recycle();
updateDrawable();
@Override
protected void drawableStateChanged()
super.drawableStateChanged();
invalidate();
@Override
public ScaleType getScaleType()
return mScaleType;
@Override
public void setScaleType(ScaleType scaleType)
super.setScaleType(scaleType);
mScaleType = scaleType;
updateDrawable();
@Override
public void setImageDrawable(Drawable drawable)
mResource = 0;
mDrawable = RoundCornerDrawable.fromDrawable(drawable, getResources());
super.setImageDrawable(mDrawable);
updateDrawable();
@Override
public void setImageBitmap(Bitmap bm)
mResource = 0;
mDrawable = RoundCornerDrawable.fromBitmap(bm, getResources());
super.setImageDrawable(mDrawable);
updateDrawable();
@Override
public void setImageResource(int resId)
if (mResource != resId)
mResource = resId;
mDrawable = resolveResource();
super.setImageDrawable(mDrawable);
updateDrawable();
@Override
public void setImageURI(Uri uri)
super.setImageURI(uri);
setImageDrawable(getDrawable());
private Drawable resolveResource()
Resources rsrc = getResources();
if (rsrc == null)
return null;
Drawable d = null;
if (mResource != 0)
try
d = rsrc.getDrawable(mResource);
catch (Resources.NotFoundException e)
Log.w(TAG, "Unable to find resource: " + mResource, e);
// Don't try again.
mResource = 0;
return RoundCornerDrawable.fromDrawable(d, getResources());
private void updateDrawable()
if (mDrawable == null)
return;
((RoundCornerDrawable) mDrawable).setScaleType(mScaleType);
((RoundCornerDrawable) mDrawable).setCornerRadii(mRadii);
((RoundCornerDrawable) mDrawable).setBorderWidth(mBorderWidth);
((RoundCornerDrawable) mDrawable).setBorderColor(mBorderColor);
((RoundCornerDrawable) mDrawable).setOval(isOval);
public float getCornerRadius()
return mLeftTopCornerRadius;
/**
* Set radii for each corner.
*
* @param leftTop The desired radius for left-top corner in dip.
* @param rightTop The desired desired radius for right-top corner in dip.
* @param leftBottom The desired radius for left-bottom corner in dip.
* @param rightBottom The desired radius for right-bottom corner in dip.
*
*/
public void setCornerRadiiDP(float leftTop, float rightTop, float leftBottom, float rightBottom)
final float density = getResources().getDisplayMetrics().density;
final float lt = leftTop * density;
final float rt = rightTop * density;
final float lb = leftBottom * density;
final float rb = rightBottom * density;
mRadii = new float[] lt, lt, rt, rt, rb, rb, lb, lb ;
updateDrawable();
public float getBorderWidth()
return mBorderWidth;
/**
* Set border width.
*
* @param width
* The desired width in dip.
*/
public void setBorderWidthDP(float width)
float scaledWidth = getResources().getDisplayMetrics().density * width;
if (mBorderWidth == scaledWidth)
return;
mBorderWidth = scaledWidth;
updateDrawable();
invalidate();
public int getBorderColor()
return mBorderColor.getDefaultColor();
public void setBorderColor(int color)
setBorderColor(ColorStateList.valueOf(color));
public ColorStateList getBorderColors()
return mBorderColor;
public void setBorderColor(ColorStateList colors)
if (mBorderColor.equals(colors))
return;
mBorderColor = (colors != null) ? colors : ColorStateList
.valueOf(DEFAULT_BORDER_COLOR);
updateDrawable();
if (mBorderWidth > 0)
invalidate();
public boolean isOval()
return isOval;
public void setOval(boolean oval)
isOval = oval;
updateDrawable();
invalidate();
static class RoundCornerDrawable extends Drawable
private static final String TAG = "RoundCornerDrawable";
private static final int DEFAULT_BORDER_COLOR = Color.BLACK;
private RectF mBounds = new RectF();
private RectF mBorderBounds = new RectF();
private final RectF mBitmapRect = new RectF();
private final int mBitmapWidth;
private final int mBitmapHeight;
private final Paint mBitmapPaint;
private final Paint mBorderPaint;
private BitmapShader mBitmapShader;
private float[] mRadii = new float[] 0, 0, 0, 0, 0, 0, 0, 0 ;
private float[] mBorderRadii = new float[] 0, 0, 0, 0, 0, 0, 0, 0 ;
private boolean mOval = false;
private float mBorderWidth = 0;
private ColorStateList mBorderColor = ColorStateList.valueOf(DEFAULT_BORDER_COLOR);
// Set default scale type to FIT_CENTER, which is default scale type of
// original ImageView.
private ScaleType mScaleType = ScaleType.FIT_CENTER;
private Path mPath = new Path();
private Bitmap mBitmap;
private boolean mBoundsConfigured = false;
public RoundCornerDrawable(Bitmap bitmap, Resources r)
mBitmap = bitmap;
mBitmapShader = new BitmapShader(bitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
if (bitmap != null)
mBitmapWidth = bitmap.getScaledWidth(r.getDisplayMetrics());
mBitmapHeight = bitmap.getScaledHeight(r.getDisplayMetrics());
else
mBitmapWidth = mBitmapHeight = -1;
mBitmapRect.set(0, 0, mBitmapWidth, mBitmapHeight);
mBitmapPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mBitmapPaint.setStyle(Paint.Style.FILL);
mBitmapPaint.setShader(mBitmapShader);
mBorderPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mBorderPaint.setStyle(Paint.Style.STROKE);
mBorderPaint.setColor(mBorderColor.getColorForState(getState(), DEFAULT_BORDER_COLOR));
mBorderPaint.setStrokeWidth(mBorderWidth);
public static RoundCornerDrawable fromBitmap(Bitmap bitmap, Resources r)
if (bitmap != null)
return new RoundCornerDrawable(bitmap, r);
else
return null;
@SuppressLint("LongLogTag")
public static Drawable fromDrawable(Drawable drawable, Resources r)
if (drawable != null)
if (drawable instanceof RoundCornerDrawable)
return drawable;
else if (drawable instanceof LayerDrawable)
LayerDrawable ld = (LayerDrawable) drawable;
final int num = ld.getNumberOfLayers();
for (int i = 0; i < num; i++)
Drawable d = ld.getDrawable(i);
ld.setDrawableByLayerId(ld.getId(i), fromDrawable(d, r));
return ld;
Bitmap bm = drawableToBitmap(drawable);
if (bm != null)
return new RoundCornerDrawable(bm, r);
else
Log.w(TAG, "Failed to create bitmap from drawable!");
return drawable;
public static Bitmap drawableToBitmap(Drawable drawable)
if (drawable == null)
return null;
if (drawable instanceof BitmapDrawable)
return ((BitmapDrawable) drawable).getBitmap();
Bitmap bitmap;
int width = Math.max(drawable.getIntrinsicWidth(), 2);
int height = Math.max(drawable.getIntrinsicHeight(), 2);
try
bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
drawable.draw(canvas);
catch (IllegalArgumentException e)
e.printStackTrace();
bitmap = null;
return bitmap;
@Override
public boolean isStateful()
return mBorderColor.isStateful();
@Override
protected boolean onStateChange(int[] state)
int newColor = mBorderColor.getColorForState(state, 0);
if (mBorderPaint.getColor() != newColor)
mBorderPaint.setColor(newColor);
return true;
else
return super.onStateChange(state);
private void configureBounds(Canvas canvas)
// I have discovered a truly marvelous explanation of this,
// which this comment space is too narrow to contain. :)
// If you want to understand what's going on here,
// See http://www.joooooooooonhokim.com/?p=289
Rect clipBounds = canvas.getClipBounds();
Matrix canvasMatrix = canvas.getMatrix();
if (ScaleType.CENTER == mScaleType)
mBounds.set(clipBounds);
else if (ScaleType.CENTER_CROP == mScaleType)
applyScaleToRadii(canvasMatrix);
mBounds.set(clipBounds);
else if (ScaleType.FIT_XY == mScaleType)
Matrix m = new Matrix();
m.setRectToRect(mBitmapRect, new RectF(clipBounds), Matrix.ScaleToFit.FILL);
mBitmapShader.setLocalMatrix(m);
mBounds.set(clipBounds);
else if (ScaleType.FIT_START == mScaleType || ScaleType.FIT_END == mScaleType
|| ScaleType.FIT_CENTER == mScaleType || ScaleType.CENTER_INSIDE == mScaleType)
applyScaleToRadii(canvasMatrix);
mBounds.set(mBitmapRect);
else if (ScaleType.MATRIX == mScaleType)
applyScaleToRadii(canvasMatrix);
mBounds.set(mBitmapRect);
private void applyScaleToRadii(Matrix m)
float[] values = new float[9];
m.getValues(values);
for (int i = 0; i < mRadii.length; i++)
mRadii[i] = mRadii[i] / values[0];
private void adjustCanvasForBorder(Canvas canvas)
Matrix canvasMatrix = canvas.getMatrix();
final float[] values = new float[9];
canvasMatrix.getValues(values);
final float scaleFactorX = values[0];
final float scaleFactorY = values[4];
final float translateX = values[2];
final float translateY = values[5];
final float newScaleX = mBounds.width()
/ (mBounds.width() + mBorderWidth + mBorderWidth);
final float newScaleY = mBounds.height()
/ (mBounds.height() + mBorderWidth + mBorderWidth);
canvas.scale(newScaleX, newScaleY);
if (ScaleType.FIT_START == mScaleType || ScaleType.FIT_END == mScaleType
|| ScaleType.FIT_XY == mScaleType || ScaleType.FIT_CENTER == mScaleType
|| ScaleType.CENTER_INSIDE == mScaleType || ScaleType.MATRIX == mScaleType)
canvas.translate(mBorderWidth, mBorderWidth);
else if (ScaleType.CENTER == mScaleType || ScaleType.CENTER_CROP == mScaleType)
// First, make translate values to 0
canvas.translate(
-translateX / (newScaleX * scaleFactorX),
-translateY / (newScaleY * scaleFactorY));
// Then, set the final translate values.
canvas.translate(-(mBounds.left - mBorderWidth), -(mBounds.top - mBorderWidth));
private void adjustBorderWidthAndBorderBounds(Canvas canvas)
Matrix canvasMatrix = canvas.getMatrix();
final float[] values = new float[9];
canvasMatrix.getValues(values);
final float scaleFactor = values[0];
float viewWidth = mBounds.width() * scaleFactor;
mBorderWidth = (mBorderWidth * mBounds.width()) / (viewWidth - (2 * mBorderWidth));
mBorderPaint.setStrokeWidth(mBorderWidth);
mBorderBounds.set(mBounds);
mBorderBounds.inset(- mBorderWidth / 2, - mBorderWidth / 2);
private void setBorderRadii()
for (int i = 0; i < mRadii.length; i++)
if (mRadii[i] > 0)
mBorderRadii[i] = mRadii[i];
mRadii[i] = mRadii[i] - mBorderWidth;
@Override
public void draw(Canvas canvas)
canvas.save();
if (!mBoundsConfigured)
configureBounds(canvas);
if (mBorderWidth > 0)
adjustBorderWidthAndBorderBounds(canvas);
setBorderRadii();
mBoundsConfigured = true;
if (mOval)
if (mBorderWidth > 0)
adjustCanvasForBorder(canvas);
mPath.addOval(mBounds, Path.Direction.CW);
canvas.drawPath(mPath, mBitmapPaint);
mPath.reset();
mPath.addOval(mBorderBounds, Path.Direction.CW);
canvas.drawPath(mPath, mBorderPaint);
else
mPath.addOval(mBounds, Path.Direction.CW);
canvas.drawPath(mPath, mBitmapPaint);
else
if (mBorderWidth > 0)
adjustCanvasForBorder(canvas);
mPath.addRoundRect(mBounds, mRadii, Path.Direction.CW);
canvas.drawPath(mPath, mBitmapPaint);
mPath.reset();
mPath.addRoundRect(mBorderBounds, mBorderRadii, Path.Direction.CW);
canvas.drawPath(mPath, mBorderPaint);
else
mPath.addRoundRect(mBounds, mRadii, Path.Direction.CW);
canvas.drawPath(mPath, mBitmapPaint);
canvas.restore();
public void setCornerRadii(float[] radii)
if (radii == null)
return;
if (radii.length != 8)
throw new ArrayIndexOutOfBoundsException("radii[] needs 8 values");
for (int i = 0; i < radii.length; i++)
mRadii[i] = radii[i];
@Override
public int getOpacity()
return (mBitmap == null || mBitmap.hasAlpha() || mBitmapPaint.getAlpha() < 255) ? PixelFormat.TRANSLUCENT
: PixelFormat.OPAQUE;
@Override
public void setAlpha(int alpha)
mBitmapPaint.setAlpha(alpha);
invalidateSelf();
@Override
public void setColorFilter(ColorFilter cf)
mBitmapPaint.setColorFilter(cf);
invalidateSelf();
@Override
public void setDither(boolean dither)
mBitmapPaint.setDither(dither);
invalidateSelf();
@Override
public void setFilterBitmap(boolean filter)
mBitmapPaint.setFilterBitmap(filter);
invalidateSelf();
@Override
public int getIntrinsicWidth()
return mBitmapWidth;
@Override
public int getIntrinsicHeight()
return mBitmapHeight;
public float getBorderWidth()
return mBorderWidth;
public void setBorderWidth(float width)
mBorderWidth = width;
mBorderPaint.setStrokeWidth(width);
public int getBorderColor()
return mBorderColor.getDefaultColor();
public void setBorderColor(int color)
setBorderColor(ColorStateList.valueOf(color));
public ColorStateList getBorderColors()
return mBorderColor;
/**
* Controls border color of this ImageView.
*
* @param colors
* The desired border color. If it's null, no border will be
* drawn.
*
*/
public void setBorderColor(ColorStateList colors)
if (colors == null)
mBorderWidth = 0;
mBorderColor = ColorStateList.valueOf(Color.TRANSPARENT);
mBorderPaint.setColor(Color.TRANSPARENT);
else
mBorderColor = colors;
mBorderPaint.setColor(mBorderColor.getColorForState(getState(),
DEFAULT_BORDER_COLOR));
public boolean isOval()
return mOval;
public void setOval(boolean oval)
mOval = oval;
public ScaleType getScaleType()
return mScaleType;
public void setScaleType(ScaleType scaleType)
if (scaleType == null)
return;
mScaleType = scaleType;
将styleable
添加到res
文件夹下的attr
文件
<declare-styleable name="RoundCornerImageView">
<attr name="sriv_left_top_corner_radius" format="dimension" />
<attr name="sriv_right_top_corner_radius" format="dimension" />
<attr name="sriv_left_bottom_corner_radius" format="dimension" />
<attr name="sriv_right_bottom_corner_radius" format="dimension" />
<attr name="sriv_border_width" format="dimension" />
<attr name="sriv_border_color" format="color" />
<attr name="sriv_oval" format="boolean" />
<attr name="android:scaleType" />
</declare-styleable>
在 XML 文件中使用:
<com.skd.stackdemo.RoundCornerImageView
android:layout_
android:layout_
android:src="@drawable/android"
android:scaleType="centerCrop"
app:sriv_left_top_corner_radius="0dp"
app:sriv_right_top_corner_radius="20dp"
app:sriv_left_bottom_corner_radius="0dp"
app:sriv_right_bottom_corner_radius="0dp"
app:sriv_oval="false" />
上述代码的输出是:
更多信息请查看这个github项目:SelectableRoundedImageView
希望对你有用
【讨论】:
以上是关于ImageView 只有一个圆角的主要内容,如果未能解决你的问题,请参考以下文章
Xamarin.iOS UITableViewCell ImageView 上的圆角