java.lang.IllegalStateException: 当我有一个 BottomNavigationBar 时片段已经添加 - 可能片段的多个实例
java.lang.IllegalStateException: Fragment already added when I have a BottomNavigationBar - maybe multiple instances of fragment
这很复杂,但是,我的应用程序中有一个部分(“运行”部分),它有一个带有 4 icons/fragments 的底部导航栏。当我第一次“运行”时一切正常。当我第二次“运行”时,只要单击导航栏的 main/default(或第一个)片段中列出的回收视图中的一个项目,应用程序就会崩溃。我收到的错误是:
java.lang.IllegalStateException: Fragment already added
我认为复杂性之一是应用程序的“运行”部分是一个片段,其中包含 BottomNavigationView。所有示例似乎都在 activity.
我读过这可能是一个一般性错误,但我确实注意到在 main/default 片段中单击 recyclerview 项目时出现的日志消息似乎是重复的,就好像有多个实例一样:
第一个运行:
2021-07-29 07:51:37.996 D/RunScenarioFragment: showDialog: dialog is null
2021-07-29 07:51:37.996 D/RunScenarioFragment: showDialog: creating new dialog
第二个运行:
2021-07-29 07:53:04.565 D/RunScenarioFragment: showDialog: dialog is null
2021-07-29 07:53:04.565 D/RunScenarioFragment: showDialog: creating new dialog
2021-07-29 07:53:04.575 D/RunScenarioFragment: showDialog: dialog is NOT null
2021-07-29 07:53:04.575 D/RunScenarioFragment: showDialog: no need to create new dialog.
2021-07-29 07:53:04.580 D/RunScenarioFragment: showDialog: dialog is NOT null
2021-07-29 07:53:04.580 D/RunScenarioFragment: showDialog: no need to create new dialog.
bottomnavigationbar中的代码如下,根据中的so似乎是合理的:
private void switchFragment(Fragment fragment) {
FragmentManager fm = getActivity().getSupportFragmentManager();
fm.beginTransaction().replace(R.id.frame_layout_run_scenario, fragment).addToBackStack(null).commit();
}
是否正在创建同一片段的多个实例?我不知道怎么会这样。我想一定是在我创建片段 w/the BottomNavigationBar 时,但这实际上只是一个导航调用。也许当我退出但又一次我只是导航离开:
navController.navigate(R.id.action_global_scenarioListFragment2);
这是我的听众:
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem menuItem) {
Fragment selectedFragment;
switch (menuItem.getItemId()) {
case R.id.runScenarioDashboardFragment: //nav_scenario_run_home
selectedFragment = new RunScenarioDashboardFragment();
break;
case R.id.runScenarioLogFragment: //nav_scenario_run_log
selectedFragment = new RunScenarioLogFragment();
break;
case R.id.runScenarioCommunicationFragment: //communication fragment
selectedFragment = new RunScenarioCommunicationFragment();
break;
default:
selectedFragment = new RunScenarioTokenFragment();
break;
}
switchFragment(selectedFragment);
return true;
}
});
更新
它似乎与我正在调用的自定义 AppCompatDialogFragment 有关。
我的底部导航代码工作正常。不是这部分代码导致了问题。是 AppCompatDialogFragment 被多次调用。
我的错。谢谢你的帮助。
在你的片段中class声明片段如下
RunScenarioDashboardFragment runScenarioDashboardFragment;
RunScenarioLogFragment runScenarioLogFragment;
RunScenarioCommunicationFragment runScenarioCommunicationFragment;
RunScenarioTokenFragment runScenarioTokenFragment
@Override
public void onCreate(@Nullable @org.jetbrains.annotations.Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
runScenarioDashboardFragment = new RunScenarioDashboardFragment();
runScenarioLogFragment = new RunScenarioLogFragment();
runScenarioCommunicationFragment = new RunScenarioCommunicationFragment();
runScenarioTokenFragment = new RunScenarioTokenFragment();
}
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
// your onCreateView implementation
}
将您的导航侦听器更新为
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem menuItem) {
Fragment selectedFragment=null;
switch (menuItem.getItemId()) {
case R.id.runScenarioDashboardFragment: //nav_scenario_run_home
selectedFragment = runScenarioDashboardFragment;
break;
case R.id.runScenarioLogFragment: //nav_scenario_run_log
selectedFragment = runScenarioLogFragment;
break;
case R.id.runScenarioCommunicationFragment: //communication fragment
selectedFragment = runScenarioCommunicationFragment;
break;
default:
selectedFragment = runScenarioTokenFragment;
break;
}
switchFragment(selectedFragment);
return true;
}
});
同时更新你的 switchFragment()
private void switchFragment(Fragment fragment) {
FragmentManager fm = getActivity().getSupportFragmentManager();
// this will popout the fragment in back stack if it was there and then
// begin the new transaction, add following code only if you add fragment to back stack
if(getSupportFragmentManager().getBackStackEntryCount()>0)
getSupportFragmentManager()..popBackStack();
fm.beginTransaction().replace(R.id.frame_layout_run_scenario, fragment).addToBackStack(null).commit();
}
或者干脆不在后台栈中添加
fm.beginTransaction().replace(R.id.frame_layout_run_scenario, fragment).commit();
不是上面的代码。这是按预期工作的。这是对导致问题的 AppCompatDialogFragment 的多次调用。上面的代码适用于 BottomNavigationView。
谢谢大家的帮助。
这很复杂,但是,我的应用程序中有一个部分(“运行”部分),它有一个带有 4 icons/fragments 的底部导航栏。当我第一次“运行”时一切正常。当我第二次“运行”时,只要单击导航栏的 main/default(或第一个)片段中列出的回收视图中的一个项目,应用程序就会崩溃。我收到的错误是:
java.lang.IllegalStateException: Fragment already added
我认为复杂性之一是应用程序的“运行”部分是一个片段,其中包含 BottomNavigationView。所有示例似乎都在 activity.
我读过这可能是一个一般性错误,但我确实注意到在 main/default 片段中单击 recyclerview 项目时出现的日志消息似乎是重复的,就好像有多个实例一样:
第一个运行:
2021-07-29 07:51:37.996 D/RunScenarioFragment: showDialog: dialog is null
2021-07-29 07:51:37.996 D/RunScenarioFragment: showDialog: creating new dialog
第二个运行:
2021-07-29 07:53:04.565 D/RunScenarioFragment: showDialog: dialog is null
2021-07-29 07:53:04.565 D/RunScenarioFragment: showDialog: creating new dialog
2021-07-29 07:53:04.575 D/RunScenarioFragment: showDialog: dialog is NOT null
2021-07-29 07:53:04.575 D/RunScenarioFragment: showDialog: no need to create new dialog.
2021-07-29 07:53:04.580 D/RunScenarioFragment: showDialog: dialog is NOT null
2021-07-29 07:53:04.580 D/RunScenarioFragment: showDialog: no need to create new dialog.
bottomnavigationbar中的代码如下,根据
private void switchFragment(Fragment fragment) {
FragmentManager fm = getActivity().getSupportFragmentManager();
fm.beginTransaction().replace(R.id.frame_layout_run_scenario, fragment).addToBackStack(null).commit();
}
是否正在创建同一片段的多个实例?我不知道怎么会这样。我想一定是在我创建片段 w/the BottomNavigationBar 时,但这实际上只是一个导航调用。也许当我退出但又一次我只是导航离开:
navController.navigate(R.id.action_global_scenarioListFragment2);
这是我的听众:
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem menuItem) {
Fragment selectedFragment;
switch (menuItem.getItemId()) {
case R.id.runScenarioDashboardFragment: //nav_scenario_run_home
selectedFragment = new RunScenarioDashboardFragment();
break;
case R.id.runScenarioLogFragment: //nav_scenario_run_log
selectedFragment = new RunScenarioLogFragment();
break;
case R.id.runScenarioCommunicationFragment: //communication fragment
selectedFragment = new RunScenarioCommunicationFragment();
break;
default:
selectedFragment = new RunScenarioTokenFragment();
break;
}
switchFragment(selectedFragment);
return true;
}
});
更新 它似乎与我正在调用的自定义 AppCompatDialogFragment 有关。
我的底部导航代码工作正常。不是这部分代码导致了问题。是 AppCompatDialogFragment 被多次调用。
我的错。谢谢你的帮助。
在你的片段中class声明片段如下
RunScenarioDashboardFragment runScenarioDashboardFragment;
RunScenarioLogFragment runScenarioLogFragment;
RunScenarioCommunicationFragment runScenarioCommunicationFragment;
RunScenarioTokenFragment runScenarioTokenFragment
@Override
public void onCreate(@Nullable @org.jetbrains.annotations.Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
runScenarioDashboardFragment = new RunScenarioDashboardFragment();
runScenarioLogFragment = new RunScenarioLogFragment();
runScenarioCommunicationFragment = new RunScenarioCommunicationFragment();
runScenarioTokenFragment = new RunScenarioTokenFragment();
}
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
// your onCreateView implementation
}
将您的导航侦听器更新为
bottomNavigationView.setOnNavigationItemSelectedListener(new BottomNavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem menuItem) {
Fragment selectedFragment=null;
switch (menuItem.getItemId()) {
case R.id.runScenarioDashboardFragment: //nav_scenario_run_home
selectedFragment = runScenarioDashboardFragment;
break;
case R.id.runScenarioLogFragment: //nav_scenario_run_log
selectedFragment = runScenarioLogFragment;
break;
case R.id.runScenarioCommunicationFragment: //communication fragment
selectedFragment = runScenarioCommunicationFragment;
break;
default:
selectedFragment = runScenarioTokenFragment;
break;
}
switchFragment(selectedFragment);
return true;
}
});
同时更新你的 switchFragment()
private void switchFragment(Fragment fragment) {
FragmentManager fm = getActivity().getSupportFragmentManager();
// this will popout the fragment in back stack if it was there and then
// begin the new transaction, add following code only if you add fragment to back stack
if(getSupportFragmentManager().getBackStackEntryCount()>0)
getSupportFragmentManager()..popBackStack();
fm.beginTransaction().replace(R.id.frame_layout_run_scenario, fragment).addToBackStack(null).commit();
}
或者干脆不在后台栈中添加
fm.beginTransaction().replace(R.id.frame_layout_run_scenario, fragment).commit();
不是上面的代码。这是按预期工作的。这是对导致问题的 AppCompatDialogFragment 的多次调用。上面的代码适用于 BottomNavigationView。
谢谢大家的帮助。