简体   繁体   English

如何在android中创建形状并在该形状上添加文本和图像?

[英]How to create shapes in android and add text and image on the shape?

I am trying to create the green shape and add text and an image on top of the green shape. 我正在尝试创建绿色形状,并在绿色形状之上添加文本和图像。 Like this example: 像这个例子: 在此处输入图片说明

I created the this example in photoshop and I tried to use it as an <ImageView> but the image always look blurry and so, I decided to re-create it using .xml 我在photoshop中创建了此示例,并尝试将其用作<ImageView>但图像始终显得模糊,因此,我决定使用.xml重新创建它。

I know how to create a circle, something like this: 我知道如何创建一个圆,像这样:

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:innerRadius="0dp"
android:shape="ring"
android:thicknessRatio="1.9"
android:useLevel="false" >
<solid android:color="@android:color/transparent" />

<stroke
    android:width="10dp"
    android:color="@android:color/white" />
</shape>

Thanks, 谢谢,

You have several options but if I understand you correctly you would like to have one View which will fill the whole screen, show some text in addition to the picture and last not least have this curved background. 您有几种选择,但是如果我对您的理解正确,那么您希望拥有一个可以覆盖整个屏幕的View ,除了显示图片之外还显示一些文本,最后还要具有弯曲的背景。

To achieve this, one can create a custom View which extends from ImageView (or as Android Studio recommends it, from android.support.v7.widget.AppCompatImageView ). 为此,可以创建一个自定义View ,该自定义ViewImageView扩展(或者如Android Studio推荐的那样,从android.support.v7.widget.AppCompatImageView扩展)。 Extending from ImageView means we'll have to take care of the background and the text, handling the picture will be no problem. ImageView扩展意味着我们必须照顾好背景和文本,处理图片不会有问题。

IMO it's better to give the custom View a set of parameters and have it draw the background using a Path than to use a ShapeDrawable because this way one can first evaluate the View 's bounds and then determine where exactly the curve should be drawn. IMO最好给自定义View一组参数,并使用Path绘制背景,而不是使用ShapeDrawable因为这样可以先评估View的边界,然后确定应该在哪里绘制曲线。

First, let's introduce some dimension values in res/values/dimens.xml 首先,让我们在res / values / dimens.xml中引入一些维度值

<dimen name="clipped_circle_deviation">100dp</dimen>
<dimen name="clipped_circle_padding_top">60dp</dimen>

Then, the Activity layout: 然后,活动布局:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
            android:layout_width="match_parent"
            android:layout_height="match_parent">
    <com.example.customviews.views.ClippedCircleView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:src="@drawable/test"
        android:paddingTop="@dimen/clipped_circle_padding_top"
        android:scaleType="center"/>
</RelativeLayout>

The picture I used for testing: 我用于测试的图片: 在此处输入图片说明

And what it looks like (I'm sure the text needs some fine tuning but that's another question) 以及它的外观(我确定文本需要一些微调,但这是另一个问题)

在此处输入图片说明

ClippedCircleView.java ClippedCircleView.java

public class ClippedCircleView extends android.support.v7.widget.AppCompatImageView {

    public static final String TAG = "ClippedCircle";
    private static final int INNER_EDGE_WEIGHT = 2;
    private static final int OUTER_EDGE_WEIGHT = 3;

    private int measuredWidth;
    private int measuredHeight;
    private Paint innerPaint;
    private Paint outerPaint,;
    private Paint textPaint;
    private Path path;

    public ClippedCircleView(Context context) {
        super(context);
        init();
    }

    public ClippedCircleView(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public ClippedCircleView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    private void init(){
        setWillNotDraw(false);

        path = new Path();

        innerPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        innerPaint.setColor(Color.GREEN);
        innerPaint.setStyle(Paint.Style.FILL);
        outerPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        outerPaint.setColor(Color.WHITE);
        outerPaint.setStyle(Paint.Style.FILL);
        textPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        textPaint.setColor(Color.WHITE);
        textPaint.setStyle(Paint.Style.FILL);
        textPaint.setTextSize(getResources().getDimensionPixelSize(R.dimen.clipped_circle_textsize));

    }

    @Override
    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
        super.onLayout(changed, left, top, right, bottom);
        measuredWidth = right - left;
        measuredHeight = bottom - top;
        float innerEdgeLength = INNER_EDGE_WEIGHT/ (OUTER_EDGE_WEIGHT * 1.0f) * measuredHeight;
        path.moveTo(0,0);
        path.lineTo(0, innerEdgeLength);
        float deviation = getResources().getDimensionPixelSize(R.dimen.clipped_circle_deviation);
        path.quadTo(measuredWidth*0.5f, innerEdgeLength + deviation, measuredWidth, innerEdgeLength);
        path.lineTo(measuredWidth, 0);
        path.lineTo(0,0);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        canvas.drawRect(0, 0, measuredWidth, measuredHeight, outerPaint);
        canvas.drawPath(path, innerPaint);
        canvas.drawText("Hello!", 32, 80, textPaint);
        canvas.drawText("Welcome to", 32, 160, textPaint);
        canvas.drawText("My App", 32, 240, textPaint);
        super.onDraw(canvas);
    }
}

There is no way to directly write text in shape drawable except converting it to bitmap then write the text. 除了将其转换为bitmap然后写入文本外,无法直接在可绘制形状中写入文本。 If you really want to create it with Drawable , you should do it using Adobe Illustrator and export it as svg . 如果您确实想使用Drawable创建它,则应该使用Adobe Illustrator进行创建并将其导出为svg Then it is possible to import svg as Android Vector Drawable (File -> New -> Vector Asset -> Local file -> ...). 然后可以将svg导入为Android Vector Drawable (文件->新建->矢量资产->本地文件-> ...)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM