You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Studio报错constant expression required,底部导航栏代码求助

问题

在Android Studio中用Java实现底部导航栏时,switch语句里的R.id.home、R.id.favorites、R.id.tools、R.id.status持续报“constant expression required”错误,相关代码如下:

MainActivity代码

package com.rpitest.appmudu;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;
import android.view.MenuItem;

import com.google.android.material.bottomnavigation.BottomNavigationView;
import com.google.android.material.navigation.NavigationBarView;

public class MainActivity extends AppCompatActivity {

    BottomNavigationView bottomNavigationView;

    HomeFragment homeFragment = new HomeFragment();
    FavoritesFragment favoritesFragment = new FavoritesFragment();
    ToolsFragment toolsFragment = new ToolsFragment();
    StatusFragment statusFragment = new StatusFragment();

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

        bottomNavigationView = findViewById(R.id.bottom_navigation);

        getSupportFragmentManager().beginTransaction().replace(R.id.container,homeFragment).commit();

        bottomNavigationView.setOnItemSelectedListener(new NavigationBarView.OnItemSelectedListener() {
            @Override
            public boolean onNavigationItemSelected(MenuItem item) {
                switch (item.getItemId()){
                    case R.id.home:
                       getSupportFragmentManager().beginTransaction().replace(R.id.container,homeFragment).commit();
                       return true;

                    case R.id.favorites:
                       getSupportFragmentManager().beginTransaction().replace(R.id.container,favoritesFragment).commit();
                       return true;

                    case R.id.tools:
                       getSupportFragmentManager().beginTransaction().replace(R.id.container,toolsFragment).commit();
                       return true;

                    case R.id.status:
                        getSupportFragmentManager().beginTransaction().replace(R.id.container,statusFragment).commit();
                        return true;

                }
               return false;
            }
        });
    }
}

菜单XML代码(menu目录下)

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

    <item android:id="@+id/home"
        android:title="Home"
        android:icon="@drawable/icon_home"/>

    <item android:id="@+id/favorites"
        android:title="favorites"
        android:icon="@drawable/icon_favorites"/>

    <item android:id="@+id/tools"
        android:title="Tools"
        android:icon="@drawable/icon_tools"/>

    <item android:id="@+id/status"
        android:title="Status"
        android:icon="@drawable/icon_status"/>
</menu>

## 解决方案
### 报错原因
Java的switch case要求case分支的值必须是**编译时常量**,但默认配置下,旧版Android Gradle插件生成的`R.id`字段不是final类型(属于运行时常量),因此触发该错误。

### 两种解决方法
#### 方法一:用if-else替代switch
直接替换switch逻辑为if-else判断,避开常量要求:
```java
@Override
public boolean onNavigationItemSelected(MenuItem item) {
    int itemId = item.getItemId();
    if (itemId == R.id.home) {
        getSupportFragmentManager().beginTransaction().replace(R.id.container, homeFragment).commit();
        return true;
    } else if (itemId == R.id.favorites) {
        getSupportFragmentManager().beginTransaction().replace(R.id.container, favoritesFragment).commit();
        return true;
    } else if (itemId == R.id.tools) {
        getSupportFragmentManager().beginTransaction().replace(R.id.container, toolsFragment).commit();
        return true;
    } else if (itemId == R.id.status) {
        getSupportFragmentManager().beginTransaction().replace(R.id.container, statusFragment).commit();
        return true;
    }
    return false;
}

方法二:让R.id成为编译时常量

如果想保留switch写法,可在模块的build.gradle(或build.gradle.kts)中添加配置,让AGP生成final类型的R字段:

android {
    buildFeatures {
        buildConfig = true
        resValues = true
    }
    // 若使用AGP 3.0~7.0版本,可替换为:
    // defaultConfig {
    //     generateBuildConfig true
    // }
}

配置完成后同步项目,R.id就会变成编译时常量,switch语句即可正常编译。


内容的提问来源于stack exchange,提问作者Andi St

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.20 22:15:20