Android : stroke in a shape create a margin of the stroke width

50,159

Solution 1

Surround your shape with <item>...</item> tags and set up top, bottom, left and right attributes of <item> with margin values you want. Then wrap whole item with a <layer-list>. See below:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:left="{L-Margin}dp"
        android:right="{R-Margin}dp"
        android:bottom="{B-Margin}dp"
        android:top="{T-Margin}dp">

        <!-- Insert your shape here: -->
        <shape android:shape="...">  
            ...
        </shape>

    </item>
</layer-list>

If you want padding (instead of margin), see Ahmad Aghazadeh answer below.

Solution 2

You can use padding Transparent instead of margin

<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
             android:id="@+id/listview_background_shape">
    <stroke 
        android:width="8dp" 
        android:color="#0000000" />
    <padding 
        android:left="2dp"
        android:top="2dp"
        android:right="2dp"
        android:bottom="2dp" />

    <solid 
        android:color="@color/white" />
</shape>

Solution 3

I had same problem and solved it like this:

<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item>
        <shape
            android:shape="rectangle">
            <solid android:color="@color/background" />
            <corners android:radius="2dp"/>
            <stroke
                android:width="4dp"
                android:color="@android:color/black" />
        </shape>
    </item>
    <item>
        <shape
            android:shape="rectangle">
            <corners android:radius="2dp"/>
            <solid android:color="@android:color/transparent" />
            <stroke
                android:width="2dp"
                android:color="@color/background" />
        </shape>
    </item>
</layer-list>

It gives two drawables with two strokes. First drawable have stroke with width (width + margin of desirable stroke). Second drawable have only visible stroke with width of desirable margin.

Share:
50,159
Anthony
Author by

Anthony

Updated on November 04, 2020

Comments

  • Anthony
    Anthony over 3 years

    I created a rectangle shape in order to use it as list item background. My problem is the stroke does not follow the view border but let a margin of +/- the stroke width.

    Here is the xml of my shape :

    <?xml version="1.0" encoding="utf-8"?>
    <shape xmlns:android="http://schemas.android.com/apk/res/android"
        android:innerRadiusRatio="1"
        android:shape="rectangle" >
        <solid android:color="@color/deminoir" />
        <stroke
            android:width="4dp"
            android:color="@color/deminoir" />
        <padding
            android:bottom="4dp"
            android:left="4dp"
            android:right="4dp"
            android:top="4dp" />
    </shape>
    

    And here is the xml of my style :

    <style name="champ">
        <item name="android:layout_width">match_parent</item>
        <item name="android:layout_height">wrap_content</item>
        <item name="android:orientation">vertical</item>
        <item name="android:background">@drawable/bordurechamp</item>
    </style>
    

    And finaly the xml of my list item view :

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        style="@style/champ" >
    
    
        <!-- titre -->
        <TextView
            android:id="@+id/titre"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="@color/deminoir"
            android:padding="5dip"
            android:text="titre"
            android:textAppearance="@android:style/TextAppearance.Large" />
    
        <!-- Contenu -->
        <TextView
            android:id="@+id/valeur"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:gravity="center_horizontal"
            android:padding="5dip"
            android:text="valeur"
            android:textAppearance="@android:style/TextAppearance.Medium"
            />
    
    </LinearLayout>