我知道这个问题可能被问了那么多,但是在我经历的所有答案中,非对我没有用。当我打算从一个活动扩展为一个NavigationDrawer活动的片段时,会出现此异常:
java.lang.IllegalArgumentException: No view found for id 0x7f0800c6 (xyz.ummo.user:id/frame) for fragment MyProfileFragment{16c76dd4 (91011ab5-3b76-4ccb-8573-f2b49ba96f08) id=0x7f0800c6 }
我已经尝试了几乎所有将屏幕从活动切换为放大为NavigationDrawerActivity的片段的方法。请仔细查看以下Java代码和xml布局(以副标题显示):
我以前打算从Activity到Fragment的方法:
public void finishEditProfile(View view){
MyProfileFragment fragment = MyProfileFragment.newInstance("param1", "param2");
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.add(R.id.frame, fragment , "");
transaction.addToBackStack(null);
transaction.commit();
}
MyProfileFragment.java,它是Fragment类:
public class MyProfileFragment extends Fragment {
// TODO: Rename parameter arguments, choose names that match
// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
private static final String ARG_PARAM1 = "param1";
private static final String ARG_PARAM2 = "param2";
// TODO: Rename and change types of parameters
private String mParam1;
private String mParam2;
private OnFragmentInteractionListener mListener;
TextView thisOneNayo;
public MyProfileFragment() {
// Required empty public constructor
}
public static MyProfileFragment newInstance(String param1, String param2) {
MyProfileFragment fragment = new MyProfileFragment();
Bundle args = new Bundle();
args.putString(ARG_PARAM1, param1);
args.putString(ARG_PARAM2, param2);
fragment.setArguments(args);
return fragment;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (getArguments() != null) {
mParam1 = getArguments().getString(ARG_PARAM1);
mParam2 = getArguments().getString(ARG_PARAM2);
}
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
final View view = inflater.inflate(R.layout.fragment_my_profile, container, false);
return view;
}
// TODO: Rename method, update argument and hook method into UI event
public void onButtonPressed(Uri uri) {
if (mListener != null) {
mListener.onFragmentInteraction(uri);
}
}
@Override
public void onAttach(Context context) {
super.onAttach(context);
if (context instanceof OnFragmentInteractionListener) {
mListener = (OnFragmentInteractionListener) context;
} else {
throw new RuntimeException(context.toString()
+ " must implement OnFragmentInteractionListener");
}
}
@Override
public void onDetach() {
super.onDetach();
mListener = null;
}
/**
* This interface must be implemented by activities that contain this
* fragment to allow an interaction in this fragment to be communicated
* to the activity and potentially other fragments contained in that
* activity.
* <p>
* See the Android Training lesson <a href=
* "http://developer.android.com/training/basics/fragments/communicating.html"
* >Communicating with Other Fragments</a> for more information.
*/
public interface OnFragmentInteractionListener {
// TODO: Update argument type and name
void onFragmentInteraction(Uri uri);
}
}
MainScreen.java类,它是容器类:
public class MainScreen extends AppCompatActivity
implements MyProfileFragment.OnFragmentInteractionListener,
NavigationView.OnNavigationItemSelectedListener{
private Fragment fragment;
private DrawerLayout drawer;
private NavigationView navigationView;
private Toolbar toolbar;
private ImageView messageIconButton;
private ProgressBar circularProgreesBarButton;
// tags used to attach the fragments
private static final String TAG_HOME = "home";
private static final String TAG_PROFILE = "profile";
private static final String TAG_PAYMENTS = "paymentMethods";
private static final String TAG_SERVICE_HISTORY = "serviceHistory";
private static final String TAG_LEGAL_TERMS = "legalTerms";
public static String CURRENT_TAG = TAG_HOME;
private boolean anyServiceInProgress = false;
private int serviceProgress = 0;
// flag to load home fragment when user presses back key
private boolean shouldLoadHomeFragOnBackPress = true;
private Handler mHandler;
// index to identify current nav menu item
public static int navItemIndex = 0;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main_screen);
toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
setTitle("Ummo");
//initialise the toolbar icons message icon and circular progress bar icon
messageIconButton = findViewById(R.id.message_icon_button);
circularProgreesBarButton = findViewById(R.id.circular_progressbar_btn);
circularProgreesBarButton.setProgress(serviceProgress);
mHandler = new Handler();
drawer = findViewById(R.id.drawer_layout);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
drawer.addDrawerListener(toggle);
toggle.syncState();
navigationView = findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
// initializing navigation menu
setUpNavigationView();
if (savedInstanceState == null) {
navItemIndex = 0;
CURRENT_TAG = TAG_HOME;
loadHomeFragment();
}
}
@Override
public void onBackPressed() {
DrawerLayout drawer = findViewById(R.id.drawer_layout);
if (drawer.isDrawerOpen(GravityCompat.START)) {
drawer.closeDrawer(GravityCompat.START);
} else {
super.onBackPressed();
}
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
@SuppressWarnings("StatementWithEmptyBody")
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
int id = item.getItemId();
if (id == R.id.nav_home) {
} else if (id == R.id.nav_profile) {
} else if (id == R.id.nav_payment_methods) {
} else if (id == R.id.nav_service_history) {
}
else if (id == R.id.nav_legal_terms) {
}
DrawerLayout drawer = findViewById(R.id.drawer_layout);
drawer.closeDrawer(GravityCompat.START);
return true;
}
@Override
public void onFragmentInteraction(Uri uri){
//you can leave it empty
}
private void loadHomeFragment() {
// if user select the current navigation menu again, don't do anything
// just close the navigation drawer
if (getSupportFragmentManager().findFragmentByTag(CURRENT_TAG) != null) {
drawer.closeDrawers();
return;
}
Runnable mPendingRunnable = new Runnable() {
@Override
public void run() {
// update the main content by replacing fragments
Fragment fragment = getHomeFragment();
FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();
fragmentTransaction.setCustomAnimations(android.R.anim.fade_in,
android.R.anim.fade_out);
fragmentTransaction.replace(R.id.frame, fragment, CURRENT_TAG);
fragmentTransaction.commitAllowingStateLoss();
}
};
// If mPendingRunnable is not null, then add to the message queue
if (mPendingRunnable != null) {
mHandler.post(mPendingRunnable);
}
//Closing drawer on item click
drawer.closeDrawers();
// refresh toolbar menu
invalidateOptionsMenu();
}
private Fragment getHomeFragment() {
switch (navItemIndex) {
case 0:
// home
setTitle("Ummo");
messageIconButton.setVisibility(View.VISIBLE);
circularProgreesBarButton.setVisibility(View.VISIBLE);
HomeFragment homeFragment = new HomeFragment();
return homeFragment;
case 1:
// My Profile
MyProfileFragment myProfileFragment = new MyProfileFragment();
messageIconButton.setVisibility(View.GONE);
circularProgreesBarButton.setVisibility(View.GONE);
setTitle("Profile");
return myProfileFragment;
case 2:
// payment methods fragment
PaymentMethodsFragment paymentMethodsFragment = new PaymentMethodsFragment();
messageIconButton.setVisibility(View.GONE);
circularProgreesBarButton.setVisibility(View.GONE);
setTitle("Payment Method");
return paymentMethodsFragment;
case 3:
// service history fragment
ServiceHistoryFragment serviceHistoryFragment = new ServiceHistoryFragment();
return serviceHistoryFragment;
case 4:
// legal terms fragment
LegalTermsFragment legalTermsFragment= new LegalTermsFragment();
return legalTermsFragment;
default:
return new HomeFragment();
}
}
private void setUpNavigationView() {
//Setting Navigation View Item Selected Listener to handle the item click of the navigation menu
navigationView.setNavigationItemSelectedListener(new NavigationView.OnNavigationItemSelectedListener() {
// This method will trigger on item Click of navigation menu
@Override
public boolean onNavigationItemSelected(MenuItem menuItem) {
//Check to see which item was being clicked and perform appropriate action
switch (menuItem.getItemId()) {
//Replacing the main content with ContentFragment Which is our Inbox View;
case R.id.nav_home:
navItemIndex = 0;
CURRENT_TAG = TAG_HOME;
break;
case R.id.nav_profile:
navItemIndex = 1;
CURRENT_TAG = TAG_PROFILE;
break;
case R.id.nav_payment_methods:
navItemIndex = 2;
CURRENT_TAG = TAG_PAYMENTS;
break;
case R.id.nav_service_history:
navItemIndex = 3;
CURRENT_TAG = TAG_SERVICE_HISTORY;
break;
case R.id.nav_legal_terms:
navItemIndex = 4;
CURRENT_TAG = TAG_LEGAL_TERMS;
break;
default:
navItemIndex = 0;
}
//Checking if the item is in checked state or not, if not make it in checked state
if (menuItem.isChecked()) {
menuItem.setChecked(false);
} else {
menuItem.setChecked(true);
}
menuItem.setChecked(true);
loadHomeFragment();
return true;
}
});
ActionBarDrawerToggle actionBarDrawerToggle = new ActionBarDrawerToggle(this, drawer, toolbar, R.string.openDrawer, R.string.closeDrawer) {
@Override
public void onDrawerClosed(View drawerView) {
// Code here will be triggered once the drawer closes as we dont want anything to happen so we leave this blank
super.onDrawerClosed(drawerView);
}
@Override
public void onDrawerOpened(View drawerView) {
// Code here will be triggered once the drawer open as we dont want anything to happen so we leave this blank
super.onDrawerOpened(drawerView);
}
};
//Setting the actionbarToggle to drawer layout
drawer.setDrawerListener(actionBarDrawerToggle);
//calling sync state is necessary or else your hamburger icon wont show up
actionBarDrawerToggle.syncState();
}
public void setAnyServiceInProgress(boolean anyServiceInProgress) {
this.anyServiceInProgress = anyServiceInProgress;
}
public void setServiceProgress(int serviceProgress) {
this.serviceProgress = serviceProgress;
}
public void goToEditProfile(View view){
TextView textViewToEdit;
String textToEdit = " ", toolBarTitle = " ";
switch(view.getId()){
case R.id.full_name:
textViewToEdit = view.findViewById(view.getId());
textToEdit = textViewToEdit.getText().toString();
toolBarTitle = "Enter your full name";
break;
case R.id.id_number:
textViewToEdit = view.findViewById(view.getId());
textToEdit = textViewToEdit.getText().toString();
toolBarTitle = "Enter your ID Number";
break;
case R.id.contact:
textViewToEdit = view.findViewById(view.getId());
textToEdit = textViewToEdit.getText().toString();
toolBarTitle = "Enter your phone number";
break;
case R.id.email:
textViewToEdit = view.findViewById(view.getId());
textToEdit = textViewToEdit.getText().toString();
toolBarTitle = "Enter your email";
break;
}
MyProfileFragment myProfileFragment = new MyProfileFragment();
Intent intent= new Intent(this, EditMyProfile.class);
String tag = myProfileFragment.getTag();
intent.putExtra(EditMyProfile.CONST_TAG, tag);
intent.putExtra("name", textToEdit);
intent.putExtra("toolBarTitle", toolBarTitle);
startActivity(intent);
}
public void finishEditrofile(View view){
Fragment fragment = new MyProfileFragment();
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.frame, fragment, "TAG_PROFILE");
transaction.addToBackStack(null);
transaction.commit();
}
}
activity_main_screen.xml是我要移动到的片段的布局:
<androidx.drawerlayout.widget.DrawerLayout 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:id="@+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true"
tools:openDrawer="start">
<include
layout="@layout/app_bar_main_screen"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
<com.google.android.material.navigation.NavigationView
android:id="@+id/nav_view"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
android:fitsSystemWindows="true"
app:theme="@style/NavigationDrawerStyle"
app:headerLayout="@layout/nav_header_main_screen"
app:menu="@menu/activity_main_screen_drawer" />
app_bar_main_screen.xml是activity_main_screen.xml的一部分,其中包含片段的容器:
<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/main"
tools:context=".MainScreen">
<com.google.android.material.appbar.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:theme="@style/AppTheme.AppBarOverlay">
<androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:background="?attr/colorPrimary"
app:popupTheme="@style/AppTheme.PopupOverlay">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="right"
android:id="@+id/message_icon_button"
android:src="@drawable/message_toolbar_icon"
android:layout_alignParentEnd="true"
android:layout_alignParentRight="true"
android:layout_marginRight="10dp"
/>
<ProgressBar
android:id="@+id/circular_progressbar_btn"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="50dp"
android:layout_height="50dp"
android:indeterminate="false"
android:max="100"
android:progress="50"
android:layout_gravity="right"
android:progressDrawable="@drawable/circular_progress_bar"
android:secondaryProgress="100"
/>
</androidx.appcompat.widget.Toolbar>
</com.google.android.material.appbar.AppBarLayout>
<FrameLayout
android:id="@+id/frame"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
</FrameLayout>