Android fragments 如何在Java项目中使用NavigationExtensions.kt?

Android fragments 如何在Java项目中使用NavigationExtensions.kt?,android-fragments,android-jetpack,android-architecture-navigation,android-jetpack-navigation,Android Fragments,Android Jetpack,Android Architecture Navigation,Android Jetpack Navigation,我正在尝试在一个新项目中使用BottomNavigation实现NavController。这是我第一次尝试,关于这件事,到处都有很多模棱两可的信息 因此,我的问题涉及到每个底部选项卡都有自己的后堆栈,并在底部导航点击之间保留片段。是的,我已经看过了,但我无法理解如何将其与我现有的Java代码集成,因为示例在Kotlin中 有人能帮我吗 好的,经过几个小时的尝试,我使用了示例Kotlin项目,然后将我的java类、资源和资产导入到这个项目中。为了更改mainactivity.kt,我对它进行了反

我正在尝试在一个新项目中使用BottomNavigation实现NavController。这是我第一次尝试,关于这件事,到处都有很多模棱两可的信息

因此,我的问题涉及到每个底部选项卡都有自己的后堆栈,并在底部导航点击之间保留片段。是的,我已经看过了,但我无法理解如何将其与我现有的Java代码集成,因为示例在Kotlin中


有人能帮我吗

好的,经过几个小时的尝试,我使用了示例Kotlin项目,然后将我的java类、资源和资产导入到这个项目中。为了更改mainactivity.kt,我对它进行了反编译,得到了以下文件。这仍然是基本的工作,但至少我已经有了框架,希望能节省一些人几个小时的挠头

package com.example.android.navigationadvancedsample;

import android.os.Bundle;

import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.LifecycleOwner;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.Observer;
import androidx.navigation.NavController;

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

import org.jetbrains.annotations.Nullable;

import java.util.List;

import kotlin.collections.CollectionsKt;


public class MainActivity extends AppCompatActivity {

private LiveData currentNavController;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate( savedInstanceState );
    getSupportActionBar().hide();
    setContentView( R.layout.activity_main );
    if (savedInstanceState == null) {
        this.setupBottomNavigationBar();
    }
}

protected void onRestoreInstanceState(@Nullable Bundle savedInstanceState) {
    super.onRestoreInstanceState( savedInstanceState );
    this.setupBottomNavigationBar();
}


void setupBottomNavigationBar() {
    BottomNavigationView bottomNavigationView = this.findViewById( R.id.bottom_nav );
    List navGraphIds = CollectionsKt.listOf( new Integer[]{R.navigation.home, R.navigation.list, R.navigation.form} );
    LiveData controller = NavigationExtensionsKt.setupWithNavController( bottomNavigationView, navGraphIds, getSupportFragmentManager(), R.id.nav_host_container, getIntent() );
    controller.observe(  this, (Observer) (new Observer() {
        // $FF: synthetic method
        // $FF: bridge method
        public void onChanged(Object var1) {
            //this.onChanged((NavController)var1);
        }

    }) );

    this.currentNavController = controller;
}

public boolean onSupportNavigateUp() {
    LiveData var10000 = this.currentNavController;
    boolean var2;
    if (var10000 != null) {
        NavController var1 = (NavController)var10000.getValue();
        if (var1 != null) {
            var2 = var1.navigateUp();
            return var2;
        }
    }

    var2 = false;
    return var2;
}
}

另一种解决方案

只需将NavigationExtensions.kt保存为java项目中的状态,并在java代码中使用即可

使用NavigationExtensions.kt文件的内容创建一个类
NavigationExtensions

还需要为Kotlin启用项目。以下是我对应用程序build.gridle所做的更改-

  • 应用插件
    应用插件:“kotlin android”
    应用插件:“kotlin android extensions”

  • 在我的依赖项中实现Kotlin扩展
    implementation'androidx.core:core ktx:1.3.1'

  • 将Kotlin JVM目标1.8添加为

    android {
        compileSdkVersion 29
        buildToolsVersion "29.0.2"
        defaultConfig {
        .........
        }
    
        compileOptions {
            sourceCompatibility 1.8
            targetCompatibility 1.8
        }
    
    
        kotlinOptions {
            jvmTarget = "1.8"
        }
    
        buildTypes {
            release {
                .......
            }
        }
    }
    
  • 这是如何在MainActivity.java中使用
    NavigationExtensions

    public class MainActivity extends AppCompatActivity {
    
        private LiveData<NavController> currentNavController = null;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
    
            BottomNavigationView bottomNavigationView = (BottomNavigationView) findViewById(R.id.bottom_nav_view);
    
            List<Integer> navGraphList = new ArrayList<>();
            navGraphList.add(R.navigation.dashboard_navigation);
            navGraphList.add(R.navigation.find_navigation);
            navGraphList.add(R.navigation.options_navigation);
    
    
            LiveData<NavController> navControllerLiveData = new NavigationExtensions().setupWithNavController(
                    bottomNavigationView
                    , navGraphList
                    , getSupportFragmentManager()
                    , R.id.fragment_container, getIntent()
            );
    
            currentNavController = navControllerLiveData;
        }
    
        @Override
        public boolean onNavigateUp() {
            currentNavController.getValue().navigateUp();
            return super.onNavigateUp();
        }
    }
    
    public类MainActivity扩展了AppCompatActivity{
    私有LiveData currentNavController=null;
    @凌驾
    创建时受保护的void(Bundle savedInstanceState){
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    BottomNavigationView BottomNavigationView=(BottomNavigationView)findViewById(R.id.bottom\u nav\u视图);
    List navGraphList=新建ArrayList();
    navGraphList.add(R.navigation.dashboard\u导航);
    navGraphList.add(R.navigation.find_导航);
    navGraphList.add(R.navigation.options\u导航);
    LiveData navControllerLiveData=new NavigationExtensions().setupWithNavController(
    底部导航视图
    ,文字学家
    ,getSupportFragmentManager()
    ,R.id.fragment_容器,getIntent()
    );
    currentNavController=navControllerLiveData;
    }
    @凌驾
    公共布尔onNavigateUp(){
    currentNavController.getValue().navigateUp();
    返回super.onNavigateUp();
    }
    }
    
    NavigationExtension文件在项目中的位置

    编辑(修复配置更改)

    要经受住配置更改(如屏幕旋转),您需要在MainActivity.java下进行以下更改

    public class MainActivity extends AppCompatActivity {
    
        private LiveData<NavController> currentNavController = null;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            if(savedInstanceState==null){
                setupBottomNavigation();
            }
            //else we need to wait for onRestoreInstanceState
        }
    
        @Override
        protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) {
            super.onRestoreInstanceState(savedInstanceState);
            setupBottomNavigation();
        }
    
        @Override
        public boolean onNavigateUp() {
            currentNavController.getValue().navigateUp();
            return super.onNavigateUp();
        }
    
        private void setupBottomNavigation(){
            BottomNavigationView bottomNavigationView = (BottomNavigationView) findViewById(R.id.bottom_nav_view);
    
            List<Integer> navGraphList = new ArrayList<>();
            navGraphList.add(R.navigation.dashboard_navigation);
            navGraphList.add(R.navigation.find_navigation);
            navGraphList.add(R.navigation.options_navigation);
    
    
            LiveData<NavController> navControllerLiveData = new NavigationExtensions().setupWithNavController(
                    bottomNavigationView
                    , navGraphList
                    , getSupportFragmentManager()
                    , R.id.fragment_container, getIntent()
            );
            currentNavController = navControllerLiveData;
        }
    }
    
    public类MainActivity扩展了AppCompatActivity{
    私有LiveData currentNavController=null;
    @凌驾
    创建时受保护的void(Bundle savedInstanceState){
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    如果(savedInstanceState==null){
    setupBottomNavigation();
    }
    //否则我们需要等待onRestoreInstanceState
    }
    @凌驾
    RestoreInstanceState(@NonNull Bundle savedInstanceState)上的受保护无效{
    super.onRestoreInstanceState(savedInstanceState);
    setupBottomNavigation();
    }
    @凌驾
    公共布尔onNavigateUp(){
    currentNavController.getValue().navigateUp();
    返回super.onNavigateUp();
    }
    私有void setupBottomNavigation(){
    BottomNavigationView BottomNavigationView=(BottomNavigationView)findViewById(R.id.bottom\u nav\u视图);
    List navGraphList=新建ArrayList();
    navGraphList.add(R.navigation.dashboard\u导航);
    navGraphList.add(R.navigation.find_导航);
    navGraphList.add(R.navigation.options\u导航);
    LiveData navControllerLiveData=new NavigationExtensions().setupWithNavController(
    底部导航视图
    ,文字学家
    ,getSupportFragmentManager()
    ,R.id.fragment_容器,getIntent()
    );
    currentNavController=navControllerLiveData;
    }
    }
    
    活动\u main.xml

    <?xml version="1.0" encoding="utf-8"?>
    <androidx.coordinatorlayout.widget.CoordinatorLayout 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:id="@+id/coordinatorLayout_main"
        tools:context=".MainActivity">
    
        <FrameLayout
            android:id="@+id/fragment_container"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_marginBottom="?attr/actionBarSize" />
    
        <com.google.android.material.bottomnavigation.BottomNavigationView
            android:id="@+id/bottom_nav_view"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:layout_gravity="bottom"
            android:background="@color/white"
            app:labelVisibilityMode="auto"
            app:itemTextColor="@drawable/bottom_nav_selector"
            app:menu="@menu/bottom_nav_menu"/>
    
    </androidx.coordinatorlayout.widget.CoordinatorLayout>
    
    
    

    快乐编码

    在花了几个小时来实现Nikhil Sharma所说的内容后,我发现底部导航栏的菜单id必须与导航xml图形文件中导航标记的每个id相同。为我工作!希望能节省别人的时间

    你能提供你的activity_main.xml吗?@AcauãPitta当然,我已经在我的编辑答案中添加了activity_main.xml:)非常感谢。我遵循了一切,我的nav_视图ID和graphs ID是相同的,但在我的例子中,当片段发生变化时,它有时会在后面继续可见。检查:这不应该,因为navController在内部使用replace()方法从一个片段切换到另一个片段,如果您仍然面临问题,您应该使用该查询创建一个问题,我或其他人可能会乐意提供帮助。不幸的是,我无法发布问题,并注意到这一点。您是否最终将代码迁移到Kotlin?