欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Android实现切换主题功能

程序员文章站 2022-05-14 21:05:46
...

现在市面上有很多app都有更换主题皮肤的功能,那么到底是怎么实现的呢?
首先我们先上一张简单效果图
Android实现切换主题功能

特别简单的实现,我们通过点击按钮切换主题

1.实现原理

实现起来特别简单,这里我们准备多个主题资源(自己适配),然后通过代码控制切换主题

项目结构
Android实现切换主题功能

2.配置styles.xml 和manifest清单

styles.xml

<resources>

    <!--正常主题-->
    <style name="LightTheme" parent="Theme.AppCompat.Light.NoActionBar">
        <item name="colorPrimary">@color/white</item>
        <item name="colorPrimaryDark">@color/colorPrimaryDark</item>
        <item name="colorAccent">@color/white</item>
        <item name="myBgColor">@color/white</item>
        <item name="background">@color/white</item>
        <item name="myTextColor">@color/white</item>
        <item name="myButtonColor">@color/black</item>
        <item name="windowActionBar">false</item>
        <item name="windowNoTitle">true</item>
    </style>
    <!--黑暗主题-->
    <style name="NightTheme" parent="Theme.AppCompat.DayNight.NoActionBar">
        <item name="colorPrimary">@color/black</item>
        <item name="colorPrimaryDark">@color/red</item>
        <item name="colorAccent">@color/black</item>
        <item name="myBgColor">@color/black</item>
        <item name="background">@color/black</item>
        <item name="myTextColor">@color/black</item>
        <item name="myButtonColor">@color/white</item>
        <item name="windowActionBar">false</item>
        <item name="windowNoTitle">true</item>
    </style>


</resources>

AndroidManifest.xml

  <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/LightTheme">//设置自定义主题
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

attr.xml

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <attr name="myBgColor" format="color" />
    <attr name="myButtonColor" format="color" />
    <attr name="myTextColor" format="color" />
</resources>

接下来我们在activity_main.xml设置

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 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:background="?attr/myBgColor"
    tools:context=".MainActivity">

    <Button
        android:id="@+id/btn_setTheme"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:background="@drawable/shape_btn"
        android:text="切换主题"
        android:textColor="?attr/myTextColor"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>

3.通过代码控制主题

我们利用 setTheme(id);的方法动态的设置主题(不过需要注意这个方法需要放到setContentView(R.layout.activity_main); 之前)
然后调用recreate();方法重启资源

我们要实现点击按钮就实现连续更换主题,我们需要记录下来更换状态,这里利用了SharedPreferences来存储更换状态。

实现代码:

public class MainActivity extends AppCompatActivity {
    private Button mBtn;
    private Boolean mUseMyTheme;

    @SuppressLint("ObsoleteSdkInt")
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.KITKAT) {
            Window window = getWindow();
            window.setFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS, WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
            getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION);
            getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
        }
        super.onCreate(savedInstanceState);
        final SharedPreferences sharedPreferences = getSharedPreferences("useMyTheme", MODE_PRIVATE);//获取主题更换状态
        mUseMyTheme = sharedPreferences.getBoolean("useMyTheme", true);//第一次默认设置为亮色主题
        if (!mUseMyTheme) {
            setTheme(R.style.NightTheme);//黑色主题
        } else {
            setTheme(R.style.LightTheme);//亮色主题
        }
        setContentView(R.layout.activity_main);
        mBtn = findViewById(R.id.btn_setTheme);
        mBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                mUseMyTheme = !mUseMyTheme;//切换主题状态
                recreate();//重启资源
                SharedPreferences.Editor editor = sharedPreferences.edit();
                editor.putBoolean("useMyTheme", mUseMyTheme);//存储主题更换状态
                editor.commit();

            }
        });
    }
}

到这里简单的实现了主题切换的功能,那大部分app的主题皮肤大多数都是要下载的,不可能把这些五花八门的样式全都都放在apk文件上,那样的话应用会很大。所以皮肤是通过网络下载的(当然可以有几套默认的皮肤)在放入资源文件夹下,实现方法也是这样。

4.附上项目源码

项目源码

相关标签: Android