Как сделать макет с закругленными углами? Я хочу применить закругленные углы к моему LinearLayout
.
1: Определите layout_bg.xml в drawables:
<?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="#B1BCBE" />
<corners android:radius="10dp"/>
<padding android:left="0dp" android:top="0dp" android:right="0dp" android:bottom="0dp" />
</shape>
2: Добавьте layout_bg.xml
в качестве фона к вашему макету
android:background="@drawable/layout_bg"
Для API 21+, использовать просмотров клипа
Закругленный контур отсечения была добавлена в класс " вид " в API 21. Увидеть это подготовка док или этот Ссылка для получения дополнительной информации.
Эта встроенная функция позволяет закругленными углами очень легко реализовать. Она работает на любой вид или макет и поддерживает правильное отсечение.
Здесь'ы что делать:
андроид:фон=на"@холст/round_outline"
вандроид:clipToOutline=то"Правда"
вК сожалению, там, кажется, ошибка и этот атрибут XML в настоящее время не признается. К счастью, мы можем установить ограничение в Java:
вид.setClipToOutline(правда)
Как Это Выглядит:
Специальное Примечание О ImageViews
setClipToOutline()
работает только при вид'ы фон установлен в виде рисунков. Если этот фон формы не существует, вид обрабатывает почву'ы план в качестве границ для отсечения и затенения целей.
Это означает, что если вы хотите закруглить углы на ImageView с setClipToOutline()
, ваше изображение должно исходить от андроида:КГД", а не " для Android:фон (так как фон используется для округлой формы). Если вы должны использовать фон, чтобы установить изображение вместо ГНЦ, вы можете использовать этот вложенных представлений обходной путь.
Вот копия XML-файла для создания drawable с белым фоном, черной рамкой и закругленными углами:
<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#ffffffff"/>
<stroke android:width="3dp"
android:color="#ff000000"
/>
<padding android:left="1dp"
android:top="1dp"
android:right="1dp"
android:bottom="1dp"
/>
<corners android:bottomRightRadius="7dp" android:bottomLeftRadius="7dp"
android:topLeftRadius="7dp" android:topRightRadius="7dp"/>
</shape>
сохраните его как xml-файл в каталоге drawable, Используйте его как любой фон drawable (иконка или файл ресурса), используя имя ресурса (R.drawable.your_xml_name).
Использовать CardView в библиотеку поддержки В7 андроид. Хотя он'немного тяжело, он решает все проблемы, и достаточно легко. Не нравится способ выигрышного фона, он может успешно подпанелей клип.
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:card_view="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
card_view:cardBackgroundColor="@android:color/transparent"
card_view:cardCornerRadius="5dp"
card_view:cardElevation="0dp"
card_view:contentPadding="0dp">
<YOUR_LINEARLAYOUT_HERE>
</android.support.v7.widget.CardView>
Я сделал так:
Проверьте скриншот:
Создайте файл drawable с именем custom_rectangle.xml
в папке drawable:
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="@android:color/white" />
<corners android:radius="10dip" />
<stroke
android:width="1dp"
android:color="@android:color/white" />
</shape>
Теперь примените фон прямоугольника к виду:
mView.setBackground(R.drawlable.custom_rectangle);
Готово
Я думаю, что лучший способ сделать это, чтобы объединить 2 вещи:
сделайте изображение макета, как показано в здесь.
сделать округлые мешочки из растрового изображения, как показано здесь
установить катры на книги.
Это будет обрабатывать случаи, что других решений не смогли решить, например, контент, который имеет углы.
Я думаю, что это's также немного больше GPU-дружески, как это показывает один слой вместо 2 .
Единственный лучший способ, чтобы сделать полностью настраиваемое представление, но, что's большое код и может занять много времени. Я думаю, что то, что я предложил здесь является лучшим из обоих миров.
Здесь'ы фрагмент, как это можно сделать:
RoundedCornersDrawable.java
/**
* shows a bitmap as if it had rounded corners. based on :
* http://rahulswackyworld.blogspot.co.il/2013/04/android-drawables-with-rounded_7.html
* easy alternative from support library: RoundedBitmapDrawableFactory.create( ...) ;
*/
public class RoundedCornersDrawable extends BitmapDrawable {
private final BitmapShader bitmapShader;
private final Paint p;
private final RectF rect;
private final float borderRadius;
public RoundedCornersDrawable(final Resources resources, final Bitmap bitmap, final float borderRadius) {
super(resources, bitmap);
bitmapShader = new BitmapShader(getBitmap(), Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
final Bitmap b = getBitmap();
p = getPaint();
p.setAntiAlias(true);
p.setShader(bitmapShader);
final int w = b.getWidth(), h = b.getHeight();
rect = new RectF(0, 0, w, h);
this.borderRadius = borderRadius < 0 ? 0.15f * Math.min(w, h) : borderRadius;
}
@Override
public void draw(final Canvas canvas) {
canvas.drawRoundRect(rect, borderRadius, borderRadius, p);
}
}
CustomView.java
public class CustomView extends ImageView {
private View mMainContainer;
private boolean mIsDirty=false;
// TODO for each change of views/content, set mIsDirty to true and call invalidate
@Override
protected void onDraw(final Canvas canvas) {
if (mIsDirty) {
mIsDirty = false;
drawContent();
return;
}
super.onDraw(canvas);
}
/**
* draws the view's content to a bitmap. code based on :
* http://nadavfima.com/android-snippet-inflate-a-layout-draw-to-a-bitmap/
*/
public static Bitmap drawToBitmap(final View viewToDrawFrom, final int width, final int height) {
// Create a new bitmap and a new canvas using that bitmap
final Bitmap bmp = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
final Canvas canvas = new Canvas(bmp);
viewToDrawFrom.setDrawingCacheEnabled(true);
// Supply measurements
viewToDrawFrom.measure(MeasureSpec.makeMeasureSpec(canvas.getWidth(), MeasureSpec.EXACTLY),
MeasureSpec.makeMeasureSpec(canvas.getHeight(), MeasureSpec.EXACTLY));
// Apply the measures so the layout would resize before drawing.
viewToDrawFrom.layout(0, 0, viewToDrawFrom.getMeasuredWidth(), viewToDrawFrom.getMeasuredHeight());
// and now the bmp object will actually contain the requested layout
canvas.drawBitmap(viewToDrawFrom.getDrawingCache(), 0, 0, new Paint());
return bmp;
}
private void drawContent() {
if (getMeasuredWidth() <= 0 || getMeasuredHeight() <= 0)
return;
final Bitmap bitmap = drawToBitmap(mMainContainer, getMeasuredWidth(), getMeasuredHeight());
final RoundedCornersDrawable drawable = new RoundedCornersDrawable(getResources(), bitmap, 15);
setImageDrawable(drawable);
}
}
Редактировать: нашел хорошую альтернативу, на основе "и RoundKornersLayouts" в библиотеке. Есть класс, который будет использоваться для всех классов макет, который вы хотите продлить, должны быть закруглены:
//based on https://github.com/JcMinarro/RoundKornerLayouts
class CanvasRounder(cornerRadius: Float, cornerStrokeColor: Int = 0, cornerStrokeWidth: Float = 0F) {
private val path = android.graphics.Path()
private lateinit var rectF: RectF
private var strokePaint: Paint?
var cornerRadius: Float = cornerRadius
set(value) {
field = value
resetPath()
}
init {
if (cornerStrokeWidth <= 0)
strokePaint = null
else {
strokePaint = Paint()
strokePaint!!.style = Paint.Style.STROKE
strokePaint!!.isAntiAlias = true
strokePaint!!.color = cornerStrokeColor
strokePaint!!.strokeWidth = cornerStrokeWidth
}
}
fun round(canvas: Canvas, drawFunction: (Canvas) -> Unit) {
val save = canvas.save()
canvas.clipPath(path)
drawFunction(canvas)
if (strokePaint != null)
canvas.drawRoundRect(rectF, cornerRadius, cornerRadius, strokePaint)
canvas.restoreToCount(save)
}
fun updateSize(currentWidth: Int, currentHeight: Int) {
rectF = android.graphics.RectF(0f, 0f, currentWidth.toFloat(), currentHeight.toFloat())
resetPath()
}
private fun resetPath() {
path.reset()
path.addRoundRect(rectF, cornerRadius, cornerRadius, Path.Direction.CW)
path.close()
}
}
Затем, в каждой из ваших пользовательских классов макет, добавить код, похожий на этот:
class RoundedConstraintLayout : ConstraintLayout {
private lateinit var canvasRounder: CanvasRounder
constructor(context: Context) : super(context) {
init(context, null, 0)
}
constructor(context: Context, attrs: AttributeSet) : super(context, attrs) {
init(context, attrs, 0)
}
constructor(context: Context, attrs: AttributeSet, defStyle: Int) : super(context, attrs, defStyle) {
init(context, attrs, defStyle)
}
private fun init(context: Context, attrs: AttributeSet?, defStyle: Int) {
val array = context.obtainStyledAttributes(attrs, R.styleable.RoundedCornersView, 0, 0)
val cornerRadius = array.getDimension(R.styleable.RoundedCornersView_corner_radius, 0f)
val cornerStrokeColor = array.getColor(R.styleable.RoundedCornersView_corner_stroke_color, 0)
val cornerStrokeWidth = array.getDimension(R.styleable.RoundedCornersView_corner_stroke_width, 0f)
array.recycle()
canvasRounder = CanvasRounder(cornerRadius,cornerStrokeColor,cornerStrokeWidth)
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR2) {
setLayerType(FrameLayout.LAYER_TYPE_SOFTWARE, null)
}
}
override fun onSizeChanged(currentWidth: Int, currentHeight: Int, oldWidth: Int, oldheight: Int) {
super.onSizeChanged(currentWidth, currentHeight, oldWidth, oldheight)
canvasRounder.updateSize(currentWidth, currentHeight)
}
override fun draw(canvas: Canvas) = canvasRounder.round(canvas) { super.draw(canvas) }
override fun dispatchDraw(canvas: Canvas) = canvasRounder.round(canvas) { super.dispatchDraw(canvas) }
}
Если вы хотите поддержать атрибутами, использовать это как написано в библиотеке:
<resources>
<declare-styleable name="RoundedCornersView">
<attr name="corner_radius" format="dimension"/>
<attr name="corner_stroke_width" format="dimension"/>
<attr name="corner_stroke_color" format="color"/>
</declare-styleable>
</resources>
Другой альтернатива, что может быть проще для большинства применений: использовать MaterialCardView . Это позволяет настроить скругленные углы, цвет обводки и ширина, и высота.
Пример:
<FrameLayout
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:layout_width="match_parent"
android:layout_height="match_parent" android:clipChildren="false" android:clipToPadding="false"
tools:context=".MainActivity">
<com.google.android.material.card.MaterialCardView
android:layout_width="100dp" android:layout_height="100dp" android:layout_gravity="center"
app:cardCornerRadius="8dp" app:cardElevation="8dp" app:strokeColor="#f00" app:strokeWidth="2dp">
<ImageView
android:layout_width="match_parent" android:layout_height="match_parent" android:background="#0f0"/>
</com.google.android.material.card.MaterialCardView>
</FrameLayout>
И результат:
Обратите внимание, что есть небольшая проблема артефактов на краях хода (листья некоторые пиксели контент есть), если вы его используете. Вы можете заметить его при увеличении. Я'вэ сообщили об этой проблеме здесь.
Редактировать: кажется, быть исправлены, но не на IDE. Сообщается здесь.
Попробуйте это...
1.создать выигрышного XML-код(custom_layout.xml):
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" >
<solid android:color="#FFFFFF" />
<stroke
android:width="2dp"
android:color="#FF785C" />
<corners android:radius="10dp" />
</shape>
2.добавьте свой вид на фоне
android:background="@drawable/custom_layout"
Если вы хотите, чтобы ваш макет округлый, лучше всего использовать CardView, он предоставил много возможностей, чтобы сделать дизайн красивый.
<android.support.v7.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
card_view:cardCornerRadius="5dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight=".3"
android:text="@string/quote_code"
android:textColor="@color/white"
android:textSize="@dimen/text_head_size" />
</LinearLayout>
</android.support.v7.widget.CardView>
С этой card_view:cardCornerRadius="в 5 диоптрий и", Вы можете изменить радиус.
Функции для заданного радиуса углу программно
static void setCornerRadius(GradientDrawable drawable, float topLeft,
float topRight, float bottomRight, float bottomLeft) {
drawable.setCornerRadii(new float[] { topLeft, topLeft, topRight, topRight,
bottomRight, bottomRight, bottomLeft, bottomLeft });
}
static void setCornerRadius(GradientDrawable drawable, float radius) {
drawable.setCornerRadius(radius);
}
Используя
GradientDrawable gradientDrawable = new GradientDrawable();
gradientDrawable.setColor(Color.GREEN);
setCornerRadius(gradientDrawable, 20f);
//or setCornerRadius(gradientDrawable, 20f, 40f, 60f, 80f);
view.setBackground(gradientDrawable);
Лучший способ сделать это было бы:
background_activity.xml
<?xml version="1.0" encoding="UTF-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:gravity="fill">
<color android:color="@color/black"/>
</item>
<item>
<shape android:gravity="fill">
<solid android:color="@color/white"/>
<corners android:radius="10dip"/>
<padding android:left="0dip" android:top="0dip" android:right="0dip" android:bottom="0dip" />
</shape>
</item>
</layer-list>
Это будет работать ниже по API 21, и дать вам что-то вроде этого:
Если вы готовы приложить немного больше усилий, более лучший контроль, а затем использовать для Андроид.поддержка.В7.виджет.CardView
с атрибутом его cardCornerRadius атрибут (и набор рельефа
до 0dp хиллингдон
, чтобы избавиться от сопровождающего тени с cardView). Кроме того, это будет работать с API уровень как низкий, как 15.
Использовать CardView, чтобы получить закругленные края для любых раскладов. Использовать : cardCornerRadius="в 5 диоптрий и quot card_view; для cardview, чтобы получить закругленные края макета.
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:card_view="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<android.support.v7.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
card_view:cardCornerRadius="5dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:padding="15dp"
android:weightSum="1">
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight=".3"
android:text="@string/quote_code"
android:textColor="@color/white"
android:textSize="@dimen/text_head_size" />
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight=".7"
android:text="@string/quote_details"
android:textColor="@color/white"
android:textSize="@dimen/text_head_size" />
</LinearLayout>
</android.support.v7.widget.CardView>
</LinearLayout>
Самый лучший и простой способ будет использовать card_background катры в макете. Это также следует в Google's материал рекомендации по проектированию. Просто включить это в вас макет:
android:background="@drawable/card_background"
Добавьте это в ваш выигрышного каталог и имя его card_background.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="#BDBDBD"/>
<corners android:radius="5dp"/>
</shape>
</item>
<item
android:left="0dp"
android:right="0dp"
android:top="0dp"
android:bottom="2dp">
<shape android:shape="rectangle">
<solid android:color="#ffffff"/>
<corners android:radius="5dp"/>
</shape>
</item>
</layer-list>
<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#FFFFFF"/>
<stroke android:width="3dip" android:color="#B1BCBE" />
<corners android:radius="10dip"/>
<padding android:left="3dip" android:top="3dip" android:right="3dip" android:bottom="3dip" />
</shape>
@Давид, просто поставить обивка же значение, как инсульт, поэтому границы могут быть видны, вне зависимости размера изображения
Я'вэ изъяты @gauravsapiens ответ с моими комментариями внутри, чтобы дать вам обоснованное опасение того, что параметров будет эффект.
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Background color -->
<solid android:color="@color/white" />
<!-- Stroke around the background, width and color -->
<stroke android:width="4dp" android:color="@color/drop_shadow"/>
<!-- The corners of the shape -->
<corners android:radius="4dp"/>
<!-- Padding for the background, e.g the Text inside a TextView will be
located differently -->
<padding android:left="10dp" android:right="10dp"
android:bottom="10dp" android:top="10dp" />
</shape>
Если вы're просто хотите создать форму, которая округляет углы, убрав отступы и ход будет делать. Если вы удалите твердые как и вы, по сути, создали закругленными углами на прозрачном фоне.
Ради того, чтобы быть ленивый я создал форму, под, которой находится только сплошной белый фон с закругленными углами - наслаждайтесь! :)
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Background color -->
<solid android:color="@color/white" />
<!-- The corners of the shape -->
<corners android:radius="4dp"/>
</shape>
Создать свой XML в мешочки, layout_background.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" >
<solid android:color="@color/your_colour" />
<stroke
android:width="2dp"
android:color="@color/your_colour" />
<corners android:radius="10dp" />
</shape>
<--width, color, radius should be as per your requirement-->
и затем добавьте это в ваш layout.xml`
android:background="@drawable/layout_background"
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:padding="@dimen/_10sdp"
android:shape="rectangle">
<solid android:color="@color/header" />
<corners
android:bottomLeftRadius="@dimen/_5sdp"
android:bottomRightRadius="@dimen/_5sdp"
android:topLeftRadius="@dimen/_5sdp"
android:topRightRadius="@dimen/_5sdp" />
</форма>