Frag On Null Exception中的Android OnBackpressed

时间:2017-02-14 19:05:21

标签: android android-fragments fragment

您好我试图覆盖后退按钮返回主页,当从BasicInfoFragment按回来然后再次回到主片段(MainFragment)时,它会给我这个错误 它给出了

java.lang.NullPointerException:尝试调用虚方法' android.support.v4.app.FragmentManager android.support.v4.app.FragmentActivity.getSupportFragmentManager()'在空对象引用上

然后应用程序粉碎

  

java.lang.NullPointerException:尝试调用虚方法' android.support.v4.app.FragmentManager android.support.v4.app.FragmentActivity.getSupportFragmentManager()'在null对象引用上                                                                                  at com.teqneia.blooddonation.BasicInfoFragment.doBack(BasicInfoFragment.java:245)                                                                                  在com.teqneia.blooddonation.MainActivity.onBackPressed(MainActivity.java:258)                                                                                  在android.app.Activity.onKeyUp(Activity.java:2530)                                                                                  在android.view.KeyEvent.dispatch(KeyEvent.java:2726)                                                                                  在android.app.Activity.dispatchKeyEvent(Activity.java:2798)                                                                                  在android.support.v7.app.AppCompatActivity.dispatchKeyEvent(AppCompatActivity.java:543)                                                                                  在android.support.v7.view.WindowCallbackWrapper.dispatchKeyEvent(WindowCallbackWrapper.java:53)                                                                                  在android.support.v7.app.AppCompatDelegateImplBase $ AppCompatWindowCallbackBase.dispatchKeyEvent(AppCompatDelegateImplBase.java:315)                                                                                  在android.support.v7.view.WindowCallbackWrapper.dispatchKeyEvent(WindowCallbackWrapper.java:53)                                                                                  在com.android.internal.policy.PhoneWindow $ DecorView.dispatchKeyEvent(PhoneWindow.java:2368)                                                                                  在android.view.ViewRootImpl $ ViewPostImeInputStage.processKeyEvent(ViewRootImpl.java:4333)                                                                                  在android.view.ViewRootImpl $ ViewPostImeInputStage.onProcess(ViewRootImpl.java:4295)                                                                                  在android.view.ViewRootImpl $ InputStage.deliver(ViewRootImpl.java:3836)                                                                                  在android.view.ViewRootImpl $ InputStage.onDeliverToNext(ViewRootImpl.java:3889)                                                                                  在android.view.ViewRootImpl $ InputStage.forward(ViewRootImpl.java:3855)                                                                                  在android.view.ViewRootImpl $ AsyncInputStage.forward(ViewRootImpl.java:3981)                                                                                  在android.view.ViewRootImpl $ InputStage.apply(ViewRootImpl.java:3863)                                                                                  在android.view.ViewRootImpl $ AsyncInputStage.apply(ViewRootImpl.java:4038)                                                                                  在android.view.ViewRootImpl $ InputStage.deliver(ViewRootImpl.java:3836)                                                                                  在android.view.ViewRootImpl $ InputStage.onDeliverToNext(ViewRootImpl.java:3889)                                                                                  在android.view.ViewRootImpl $ InputStage.forward(ViewRootImpl.java:3855)                                                                                  在android.view.ViewRootImpl $ InputStage.apply(ViewRootImpl.java:3863)                                                                                  在android.view.ViewRootImpl $ InputStage.deliver(ViewRootImpl.java:3836)                                                                                  在android.view.ViewRootImpl $ InputStage.onDeliverToNext(ViewRootImpl.java:3889)                                                                                  在android.view.ViewRootImpl $ InputStage.forward(ViewRootImpl.java:3855)                                                                                  在android.view.ViewRootImpl $ AsyncInputStage.forward(ViewRootImpl.java:4014)                                                                                  在android.view.ViewRootImpl $ ImeInputStage.onFinishedInputEvent(ViewRootImpl.java:4175)                                                                                  在android.view.inputmethod.InputMethodManager $ PendingEvent.run(InputMethodManager.java:2378)                                                                                  在android.view.inputmethod.InputMethodManager.invokeFinishedInputEventCallback(InputMethodManager.java:1999)                                                                                  在android.view.inputmethod.InputMethodManager.finishedInputEvent(InputMethodManager.java:1990)                                                                                  在android.view.inputmethod.InputMethodManager $ ImeInputEventSender.onInputEventFinished(InputMethodManager.java:2355)                                                                                  在android.view.InputEventSender.dispatchInputEventFinished(InputEventSender.java:141)                                                                                  在android.os.MessageQueue.nativePollOnce(本机方法)                                                                                  在android.os.MessageQueue.next(MessageQueue.java:330)                                                                                  在android.os.Looper.loop(Looper.java:137)                                                                                  在android.app.ActivityThread.main(ActivityThread.java:5546)                                                                                  at java.lang.reflect.Method.invoke(Native Method)                                                                                  在com.android.internal.os.ZygoteInit $ MethodAndArgsCaller.run(ZygoteInit.java:794)                                                                                  在com.android.internal.os.ZygoteInit.main(ZygoteInit.java:684)

BasicInfoFragment java

public class BasicInfoFragment extends Fragment implements MainActivity.OnBackPressedListener, View.OnClickListener {
.
.

public BasicInfoFragment() {
}


@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    View view = inflater.inflate(R.layout.fragment_basic_info, container, false);

    initialize(view);

    // Inflate the layout for this fragment
    return view;
}

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    ((MainActivity) getActivity()).setOnBackPressedListener(this);
}

void initialize(View view) {
    //VIEW OLD DATA AND ADD LISTENERS
    name = (EditText) view.findViewById(R.id.name_edit);

    email = (EditText) view.findViewById(R.id.email_edit);
    mobile = (EditText) view.findViewById(R.id.mobile_edit);
    LastDonation = (EditText) view.findViewById(R.id.date_edit);
    LastDonation.setInputType(InputType.TYPE_NULL);
    LastDonation.requestFocus();
    LastDonation.setOnClickListener(this);

    //TAKE DATA FROM SERVER
    //name.setText("");
    //email.setText();
    //mob.setText();
    //LastDonation.setText();

    b = (Button) view.findViewById(R.id.save_edit);
    b.setOnClickListener(this);
    //get Radio Groups

    radioBgGroup = (RadioGroup) view.findViewById(R.id.bg_edit);
    radioRhGroup = (RadioGroup) view.findViewById(R.id.rh_edit);

    if (mSharedGetter.getBloodType().equals("A")) {

}





@Override
public void doBack() {
    Fragment fragment = null;
    fragment = new MainFragment();
    FragmentManager fm = getActivity().getSupportFragmentManager();
    FragmentTransaction transaction = fm.beginTransaction();
    transaction.replace(R.id.fragment_container, fragment);
    transaction.commit();
}
  

MainActivity

public class MainActivity extends AppCompatActivity
        implements NavigationView.OnNavigationItemSelectedListener {

    .
            .
            .
            .
            .
            .
    protected OnBackPressedListener onBackPressedListener;


    public interface OnBackPressedListener {
        void doBack();
    }

    public void setOnBackPressedListener(OnBackPressedListener onBackPressedListener) {
        this.onBackPressedListener = onBackPressedListener;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);


        //Initially Load MainFFragment xml
        setContentView(R.layout.activity_main);
        Fragment fragment = new MainFragment();
        //Apply fragment
        FragmentTransaction fragmentTransaction =
                getSupportFragmentManager().beginTransaction();
        fragmentTransaction.replace(R.id.fragment_container, fragment);
        fragmentTransaction.commit();


        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);


        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);

        ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
                this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
        drawer.setDrawerListener(toggle);
        toggle.syncState();

        NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
        View header = navigationView.getHeaderView(0);
        TVnav_name = (TextView) header.findViewById(R.id.nav_name);
        navigationView.setNavigationItemSelectedListener(this);
        TVnav_name.setText(mSharedGetter.getUserName());
    }


    @Override
    public void onBackPressed() {
        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        if (drawer.isDrawerOpen(GravityCompat.START)) {
            drawer.closeDrawer(GravityCompat.START);
        } else if (onBackPressedListener != null)
            onBackPressedListener.doBack();
        else
            super.onBackPressed();
    }

    @Override
    protected void onDestroy() {
        onBackPressedListener = null;
        super.onDestroy();
    }

    @SuppressWarnings("StatementWithEmptyBody")
    @Override
    public boolean onNavigationItemSelected(MenuItem item) {
        // Handle navigation view item clicks here.
        int id = item.getItemId();
        Fragment fragment = null;


        if (id == R.id.nav_edit_info) {

            fragment = new BasicInfoFragment();
            if (fragment != null) {
                //Apply fragment
                FragmentTransaction fragmentTransaction =
                        getSupportFragmentManager().beginTransaction();
                fragmentTransaction.replace(R.id.fragment_container, fragment);
                fragmentTransaction.commit();
            }


        } else if (id == R.id.nav_home) {
            fragment = new MainFragment();

            if (fragment != null) {
                //Apply fragment
                FragmentTransaction fragmentTransaction =
                        getSupportFragmentManager().beginTransaction();
                fragmentTransaction.replace(R.id.fragment_container, fragment, "MY_FRAGMENT");
                fragmentTransaction.commit();
            }
        }


        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        drawer.closeDrawer(GravityCompat.START);
        return true;
    }


}
  

MainFragment

public class MainFragment extends Fragment{



    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        // Inflate the layout for this fragment
        View view = inflater.inflate(R.layout.fragment_main, container, false);





        return view;
    }





        //DIALOG BUILDER
        new AlertDialog.Builder(getActivity())
                .setTitle("DONATION REQUEST")
                .setView(dialogView)
                .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                    }
                })
                .setPositiveButton("Request now", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                        //Send the request

                        Dialog f = (Dialog) dialog;

                    }
                }).show();


    }


}

4 个答案:

答案 0 :(得分:1)

db.UserImageLists方法doBack中的

返回null。您也可以拨打getFragmentManager() from a Fragment,也不需要它。这是如何做到这一点,用更少的线。

getActivity()

答案 1 :(得分:1)

你在BasicInfoFragment中的

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    ((MainActivity) getActivity()).setOnBackPressedListener(this);
}

MainFragment应该有相同的行,否则如你所描述的那样按两次会调用BasicInfoFragment doBack()两次。

由于您在第一次单击后将其从活动中分离,因此当第二次返回时,getActivity()会从此处获取空值:

FragmentManager fm = getActivity().getSupportFragmentManager();

答案 2 :(得分:0)

总是这样打电话。

//In Activity
FragmentManager fm = getSupportFragmentManager();

//In Fragment 
FragmentManager fm = getActivity().getFragmentManager();

//For Nested Fragments 
FragmentManager fm = getChildFragmentManager();

答案 3 :(得分:0)

我认为如果你描述你想要解决的问题会更好。我相信你可能在片段的工作方式和后端栈的管理方面存在错误。

我认为问题是你的后退事件正在被触发,但这会弹出片段,但引用仍然存在。

看看: https://aarcoraci.wordpress.com/2017/02/13/android-tutorial-drawer-and-fragment-navigation-made-easyier/