android - 如何在android中在中心画一个圆

标签 android android-layout android-fragments android-linearlayout android-canvas

我希望圆形图像位于中心。
如何让它在设备的中心?

我不想使用相对布局。我已经准备好尝试了,但是它需要一个硬编码的圆圈值;因此。它不适用于所有设备。 我试图通过 LinearLayout 实现它(使用 android:layout_weight 属性) 我试过 android:layout_gravity="center",android:gravity="center" 但圆圈仍然不会到达中心。 我已附上屏幕以供引用

enter image description here

我希望圆圈位于父中心

我的 xml 是:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res/com.example.dd"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_gravity="center"
    android:orientation="vertical" >

    <LinearLayout
        android:id="@+id/LinearLayout02"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
       android:layout_gravity="center"  
        android:orientation="horizontal" >

        <Button
            android:id="@+id/Button04"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="left1" >
        </Button>

        <com.example.dd.CircularImageView
            android:id="@+id/round"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:src="@drawable/buttonarea"
            app:border="true"
            app:border_color="#323232"
            app:border_width="55dp"
            app:shadow="true" />

        <Button
            android:id="@+id/Button08"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="right" >
        </Button>
    </LinearLayout>

</LinearLayout>

我的循环类是:

     public class CircularImageView extends ImageView {
        private int borderWidth;
        private int canvasSize;
        private Bitmap image;
        private Paint paint;
        private Paint paintBorder;

        public CircularImageView(final Context context) {
            this(context, null);
        }

        public CircularImageView(Context context, AttributeSet attrs) {
            this(context, attrs, R.attr.circularImageViewStyle);
        }

        public CircularImageView(Context context, AttributeSet attrs, int defStyle) {
            super(context, attrs, defStyle);

            // init paint
            paint = new Paint();
            paint.setAntiAlias(true);

            paintBorder = new Paint();
            paintBorder.setAntiAlias(true);

            // load the styled attributes and set their properties
            TypedArray attributes = context.obtainStyledAttributes(attrs, R.styleable.CircularImageView, defStyle, 0);

            if(attributes.getBoolean(R.styleable.CircularImageView_border, true)) {
                int defaultBorderSize = (int) (4 * getContext().getResources().getDisplayMetrics().density + 0.5f);
                setBorderWidth(attributes.getDimensionPixelOffset(R.styleable.CircularImageView_border_width, defaultBorderSize));
                setBorderColor(attributes.getColor(R.styleable.CircularImageView_border_color, Color.WHITE));
            }

            if(attributes.getBoolean(R.styleable.CircularImageView_shadow, false))
                addShadow();
        }

        public void setBorderWidth(int borderWidth) {
            Log.d("TAG","::::::::::::borderWidth"+borderWidth);
            this.borderWidth = borderWidth;
            this.requestLayout();
            this.invalidate();
        }

        public void setBorderColor(int borderColor) {
            if (paintBorder != null)
                paintBorder.setColor(borderColor);
            this.invalidate();
        }

    public void addShadow() {
        setLayerType(LAYER_TYPE_SOFTWARE, paintBorder);
        paintBorder.setShadowLayer(4.0f, 0.0f, 2.0f, Color.BLACK);
    }

    @Override
    public void onDraw(Canvas canvas) {
        // load the bitmap
        image = drawableToBitmap(getDrawable());

        // init shader
        if (image != null) {

            canvasSize = canvas.getWidth();
            Log.d("TAG","::::::::::::canvasSize"+canvasSize);
            if(canvas.getHeight()<canvasSize)
                canvasSize = canvas.getHeight();

            BitmapShader shader = new BitmapShader(Bitmap.createScaledBitmap(image, canvasSize, canvasSize, false), Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
            paint.setShader(shader);

            // circleCenter is the x or y of the view's center
            // radius is the radius in pixels of the cirle to be drawn
            // paint contains the shader that will texture the shape
            int circleCenter = (canvasSize - (borderWidth * 2)) / 2;
            canvas.drawCircle(circleCenter + borderWidth, circleCenter + borderWidth, ((canvasSize - (borderWidth * 2)) / 2) + borderWidth - 4.0f, paintBorder);
            canvas.drawCircle(circleCenter + borderWidth, circleCenter + borderWidth, ((canvasSize - (borderWidth * 2)) / 2) - 4.0f, paint);
        }
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        int width = measureWidth(widthMeasureSpec);
        int height = measureHeight(heightMeasureSpec);
        setMeasuredDimension(width, height);
    }

    private int measureWidth(int measureSpec) {
        int result = 0;
        int specMode = MeasureSpec.getMode(measureSpec);
        int specSize = MeasureSpec.getSize(measureSpec);

        if (specMode == MeasureSpec.EXACTLY) {
            // The parent has determined an exact size for the child.
            result = specSize;
        } else if (specMode == MeasureSpec.AT_MOST) {
            // The child can be as large as it wants up to the specified size.
            result = specSize;
        } else {
            // The parent has not imposed any constraint on the child.
            result = canvasSize;
        }

        return result;
    }

    private int measureHeight(int measureSpecHeight) {
        int result = 0;
        int specMode = MeasureSpec.getMode(measureSpecHeight);
        int specSize = MeasureSpec.getSize(measureSpecHeight);

        if (specMode == MeasureSpec.EXACTLY) {
            // We were told how big to be
            result = specSize;
        } else if (specMode == MeasureSpec.AT_MOST) {
            // The child can be as large as it wants up to the specified size.
            result = specSize;
        } else {
            // Measure the text (beware: ascent is a negative number)
            result = canvasSize;
        }

        return (result + 2);
    }


    public Bitmap drawableToBitmap(Drawable drawable) {
                if (drawable == null) {
                    return null;
                } else if (drawable instanceof BitmapDrawable) {
                    return ((BitmapDrawable) drawable).getBitmap();
                }

                Bitmap bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(),
                        drawable.getIntrinsicHeight(), Bitmap.Config.ARGB_8888);
                Canvas canvas = new Canvas(bitmap);
                drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
                drawable.draw(canvas);

                return bitmap;
            }

我的 attrs.xml 包含以下值:

<?xml version="1.0" encoding="utf-8"?>

    <resources>

        <declare-styleable name="CircularImageView">
            <attr name="border" format="boolean"></attr>
            <attr name="border_width" format="dimension"></attr>
            <attr name="border_color" format="color"></attr>
            <attr name="shadow" format="boolean"></attr>
        </declare-styleable>

        <declare-styleable name="Theme">
            <attr name="circularImageViewStyle" format="reference"></attr>
        </declare-styleable>

    </resources>

最佳答案

使用一些假布局并将可见性设置为不可见。这应该可以解决问题。

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res/com.example.dd"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:orientation="vertical" >

<LinearLayout
    android:id="@+id/LinearLayout02"
    android:layout_width="fill_parent"
    android:layout_height="match_parent"
    android:layout_gravity="center"
    android:orientation="horizontal" >

    <Button
        android:id="@+id/Button04"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        android:text="left1" >
    </Button>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_weight="1"
        android:orientation="vertical" >

        <Button
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:orientation="vertical"
            android:text="dummy"
            android:visibility="invisible" >
        </Button>

        <Button
            android:id="@+id/round"
            android:layout_width="fill_parent"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:background="@android:drawable/star_on"
            app:shadow="true" />

        <Button
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:orientation="vertical"
            android:text="dummy"
            android:visibility="invisible" >
        </Button>
    </LinearLayout>

    <Button
        android:id="@+id/Button08"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        android:text="right" >
    </Button>
 </LinearLayout>

</LinearLayout>

关于android - 如何在android中在中心画一个圆,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27511524/

相关文章:

android - 如何使用 Android 指南针方向瞄准 opengl 相机?

java - 如何在将列表项添加到 ListView 之前以编程方式设置列表项中的字体大小?

android - 当用户点击播放按钮时我想要视频自动播放视频播放

android - 更改 RecyclerView 中不同 View 的布局管理器

Android ScrollView scrollTo() 方法不适用于 TextView?

java - Androidannotations EBean注释类应该有一个带有一个Context类型参数的构造函数

android - 如何手动安装 google api 从 3 到 7?

java - 如何通过重写接口(interface)实现Fragment-Activity通信?

android - 应用程序在后台时关闭 DialogFragment 的正确方法

Android:使用 Viewpager 将 Activity 置于最前面的通知