2

I want to make custom Info window for google map I can make it but I am not able to make triangle bellow layout. I can add image there but layout have shadow on outer line. Anyone suggest me what to do. how to make portion inside red area. as you can see outer layout have shadow.

enter image description here

Gabriele Mariotti
  • 320,139
  • 94
  • 887
  • 841
Mukesh Y.
  • 869
  • 1
  • 16
  • 36
  • 2
    please check this link [Android how to create triangle and rectangle shape programmatically?](http://stackoverflow.com/questions/22042603/android-how-to-create-triangle-and-rectangle-shape-programmatically) –  May 02 '17 at 13:01

7 Answers7

4

You can use the Material Component Library to create custom shapes.
The library provides the TriangleEdgeTreatment which creates a triangle treatment of the given size, which faces inward or outward relative to the shape.

You can use something like:

TriangleEdgeTreatment triangleEdgeTreatment = new TriangleEdgeTreatment(radius,false);

LinearLayout linearLayout= findViewById(R.id.xxxx);
ShapeAppearanceModel shapeAppearanceModel = new ShapeAppearanceModel()
    .toBuilder()
    .setBottomEdge(triangleEdgeTreatment)
    .build();

MaterialShapeDrawable shapeDrawable = new MaterialShapeDrawable(shapeAppearanceModel);
ViewCompat.setBackground(linearLayout,shapeDrawable);

enter image description here

Also for edge treatments the parent view must disable clipping of children by setting android:clipChildren="false" in xml.clipToPadding may also need to be false if there is any padding on the parent that could intersect the shadow.

Gabriele Mariotti
  • 320,139
  • 94
  • 887
  • 841
4

This can be achieved using MaterialCardView and Shape theming.

Dependency: (Use the latest stable version)

def materialVersion = '1.3.0'

implementation "com.google.android.material:material:$materialVersion"

Layout:

<LinearLayout
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:orientation="vertical">

    <com.google.android.material.card.MaterialCardView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        app:cardBackgroundColor="@color/backgroundWhite"
        app:cardElevation="4dp"
        app:cardCornerRadius="8dp">

        //Content layout here          

    </com.google.android.material.card.MaterialCardView>

    <com.google.android.material.card.MaterialCardView
        style="@style/PointerCardViewStyle"
        android:layout_width="20dp"
        android:layout_height="10dp"
        app:cardBackgroundColor="@color/whiteColor"
        android:layout_gravity="center"
        app:cardElevation="4dp" />
</LinearLayout>

Style:

<style name="PointerCardViewStyle" parent="Widget.MaterialComponents.CardView">
    <item name="shapeAppearanceOverlay">@style/ShapeAppearanceOverlayPointerCardView</item>
</style>

<style name="ShapeAppearanceOverlayPointerCardView" parent="@style/Widget.MaterialComponents.CardView">
    <item name="cornerFamily">cut</item>
    <item name="cornerSizeTopRight">0dp</item>
    <item name="cornerSizeTopLeft">0dp</item>
    <item name="cornerSizeBottomRight">10dp</item>
    <item name="cornerSizeBottomLeft">10dp</item>
</style>

Result:

Result

Xid
  • 4,578
  • 2
  • 13
  • 35
3

You can create this custom shape using <layer-list>. Below is a working example. Put custom_triangular_shape.xml into your res/drawable folder.

custom_triangular_shape.xml

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">

    <!-- Transparent Rectangle -->
    <item>
        <shape android:shape="rectangle">
            <size
                android:width="300dp"
                android:height="80dp" />
            <solid android:color="@android:color/transparent" />
        </shape>
    </item>

    <!-- Colored Rectangle -->
    <item
        android:bottom="20dp">
        <shape android:shape="rectangle">
            <corners
                android:radius="4dp">

            </corners>
            <size
                android:width="300dp"
                android:height="80dp" />
            <solid android:color="#FFFFFF" />
        </shape>
    </item>

    <!-- Bottom Triangle -->
    <item
        android:left="90dp"
        android:right="110dp"
        android:top="0dp"
        android:bottom="30dp">
        <rotate android:fromDegrees="45">
            <shape android:shape="rectangle">
                <solid android:color="#FFFFFF" />
            </shape>
        </rotate>
    </item>

</layer-list>

USE:

<LinearLayout
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:background="@drawable/custom_triangular_shape">

</LinearLayout>

OUTPUT:

enter image description here

Hope this will help~

Ferdous Ahamed
  • 21,438
  • 5
  • 52
  • 61
  • this anwer very close to my question but on thing missing that I have mention it also have the shadow effect. If I will give it shadow then inner rectangle also have shadow which i don't want. I just want show of outer line. please suggest me. if you have anything. – Mukesh Y. May 03 '17 at 06:04
  • For shadow you have to add another 2 rect with top padding. – Ferdous Ahamed May 03 '17 at 06:08
  • can you please make changes in your code. As I am very new to android. – Mukesh Y. May 03 '17 at 06:11
  • have thought about that. btw I have achieved by myself but if you have anything new please update – Mukesh Y. May 23 '17 at 08:46
  • Google's window will size based on inner content. Here you are hard coding a size into the layer list. Not exactly the same. – lostintranslation Jan 21 '19 at 23:58
2

Try this:

For triangle :

    <?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item>
        <rotate
            android:fromDegrees="45"
            android:pivotX="-40%"
            android:pivotY="87%"
            android:toDegrees="45">
            <shape android:shape="rectangle">
                <stroke
                    android:width="10dp"
                    android:color="@android:color/transparent" />
                <solid android:color="#000000" />
            </shape>
        </rotate>
    </item>
</layer-list>

For rectangle:

    <?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="#B2E3FA" />
        </shape>
    </item>
</layer-list>

Use both xml in the Layout :

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

    <RelativeLayout
        android:id="@+id/rlv1"
        android:layout_width="150dp"
        android:layout_height="50dp"
        android:background="@drawable/rectringle" />
    <RelativeLayout
        android:id="@+id/rlv2"
        android:layout_width="50dp"
        android:layout_height="50dp"
        android:layout_below="@+id/rlv1"
        android:layout_marginLeft="30dp"
        android:background="@drawable/tringle"
        android:rotation="180" />
</LinearLayout>
Sonam Gupta
  • 341
  • 1
  • 12
  • i am up voting for your effort but there are lots thing you have ignored like shadow to outer line. that case your method will not work. – Mukesh Y. May 23 '17 at 08:45
0

You can make use of layer-list. Create a triangular shape at the bottom, then create a rectangular shape as next layer and give bottom margin that matches your triangle's height.

here is a sample to make triangle shape. https://stackoverflow.com/a/18421795/1987045

Community
  • 1
  • 1
rahulrvp
  • 2,006
  • 1
  • 19
  • 26
-1

You can use a 9patch as background for your custom layout.

Lionel Briand
  • 1,732
  • 2
  • 13
  • 21
-1

Using PopUpWindow you can achieve your goal. Here is a good link to start with.

Community
  • 1
  • 1
user320676
  • 394
  • 2
  • 19
  • I don't want to know how to achieve the custom info window.I just want to know how to make a layout look similar like given image. – Mukesh Y. May 02 '17 at 12:36