如何模拟 Android API 中低于 21 的按钮高度(阴影)?

How can I emulate button elevation (shadow) in Android API lower than 21?

我有这个最小的 Android Studio 项目,只有一个按钮。 我为按钮分配了一个阴影:

android:elevation="3dp"
android:translationZ="3dp"
android:stateListAnimator="@null"

我在 Android Studio 设计选项卡中看到了阴影。但我也在 xml 编辑器

中收到警告

Atribute ... is only used in API level 21 and higher (current min is 16)

事实上,按钮阴影仅在具有 API level 21 or higher 的模拟器中显示,并且显示为平面,在具有 API level lower than 21 的模拟器中完全没有阴影。

所以具体的问题是,如何模拟 API's lower than 21 中的阴影效果。

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto">

    <LinearLayout
        android:id="@+id/main_layout"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:weightSum="1">

        <RelativeLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_margin="20dp"
            android:layout_weight="2.24">

            <Button
                android:id="@+id/my_button"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_centerHorizontal="true"
                android:layout_marginLeft="20dp"
                android:layout_marginBottom="20dp"
                android:elevation="5dp"
                android:translationZ="5dp"
                android:stateListAnimator="@null"
                android:background="@android:color/holo_green_light"
                android:text="BUTTON"/>

        </RelativeLayout>
    </LinearLayout>
</ScrollView>

MainActivity.java

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }

}

显示阴影的按钮,在 API 22 中:

API 16 中的相同按钮未显示阴影:

对于 Pre-LolliPop 设备,您必须使用可绘制文件创建阴影或高程。这条路

在您的文件夹中创建 drawable 文件,如 element_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>

然后将以下代码添加到您想要的元素中。

android:background="@drawable/element_background"

如果你愿意,可以试试 Carbon。它是一个将 material 功能反向移植到 2.2 的库。它还支持高度和生成的动画阴影。

https://github.com/ZieIony/Carbon