【问题标题】:How to apply Back button pressed in fragment [duplicate]如何应用片段中按下的后退按钮[重复]
【发布时间】:2015-12-05 06:32:49
【问题描述】:

我是安卓新手。我无法处理 onBackPressed 方法。我有一个 Activity 类,它有四个片段,如 A、B、C、D。当我吃午饭时,默认情况下,片段 A 处于活动状态,片段 A 上有链接可以移动另一个片段。我想当从片段 A 移动另一个片段(如 B、C、D)并按下返回按钮时,它返回到片段 A,如果我从片段 A 按下返回按钮,它会显示一个对话框。 我使用 onBackPressed() 如下所示

public void onBackPressed() {
    AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(
            MainActivity.this);

    // set title
    alertDialogBuilder.setTitle("Exit");

    // set dialog message
    AlertDialog.Builder builder = alertDialogBuilder
            .setMessage("Do you really want to exit?")
            .setCancelable(false)
            .setPositiveButton("Yes", new DialogInterface.OnClickListener() {
                public void onClick(DialogInterface dialog, int id) {
                    // if this button is clicked, close
                    // current activity
                    MainActivity.this.finish();
                }
            })
            .setNegativeButton("No", new DialogInterface.OnClickListener() {
                public void onClick(DialogInterface dialog, int id) {
                    // if this button is clicked, just close
                    // the dialog box and do nothing
                    dialog.cancel();
                }
            });

    // create alert dialog
    AlertDialog alertDialog = alertDialogBuilder.create();

    // show it
    alertDialog.show();
}

但它适用于所有片段,我只想使用片段 A

【问题讨论】:

  • 你有办法判断片段 A 何时显示?
  • 是的,当片段 A 显示为一个时
  • 检查我的答案,让我知道你是否克服了

标签: java android android-fragments onbackpressed


【解决方案1】:

您必须仅在 Activity 的 onBackPressed 中处理此类要求。我通常遵循以下方法:

我保留一个定义了所有片段的枚举和一个跟踪当前片段的参数:

enum FRAGMENTS{
    fragmentA, fragmentB, fragmentC, fragmentD
}
FRAGMENTS mCurrentFragment;

现在你改变片段的逻辑应该有:

public void changeFragment(FRAGMENTS newFragment){
    //Your logic
    mCurrentFragment = newFragment;
}

最后是 onBackPressed 的逻辑:

onBackPressed{
     if(mCurrentFragment == FRAGMENTS.fragmentA){
          //Your code here of asking the user if he/she really wants to quit
          super.onBackPressed();
     }else{
          changeFragment(getPreviousFragment(mCurrentFragment));
     }
}

如果您不想使用枚举,您可以使用 final int 或任何其他字符串值来表示不同的片段,并使用 mCurrentFragment 参数来跟踪显示的 currentFragment,然后您可以轻松地使用 Activity 中的代码onBackPressed 方法

如果您需要更多说明,请告诉我。

【讨论】:

    【解决方案2】:

    在替换时将片段添加到backStack

    Fragment newFragment = new ExampleFragment();
    FragmentTransaction transaction = getFragmentManager().beginTransaction();
    
    // Replace whatever is in the fragment_container view with this fragment,
    // and add the transaction to the back stack if needed
    transaction.replace(R.id.fragment_container, newFragment);
    transaction.addToBackStack(null);
    
    // Commit the transaction
    transaction.commit();
    

    然后在一个Activity中重写onBackPressed方法

    【讨论】:

      【解决方案3】:

      所以这是您正在寻找的答案:)

      方法一

       @Override
       public boolean onKeyDown(int keyCode, KeyEvent event) {
          if (keyCode == KeyEvent.KEYCODE_BACK) {
      
              // Your stuff here
              AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(MainActivity.this);
      
              // set title
              alertDialogBuilder.setTitle("Exit");
      
              // set dialog message
              AlertDialog.Builder builder = alertDialogBuilder.setMessage("Do you really want to exit?")
                      .setCancelable(false).setPositiveButton("Yes", new DialogInterface.OnClickListener() {
                          public void onClick(DialogInterface dialog, int id) {
                              // if this button is clicked, close
                              // current activity
      
                              System.exit(0);
                          }
                      }).setNegativeButton("No", new DialogInterface.OnClickListener() {
                          public void onClick(DialogInterface dialog, int id) {
                              // if this button is clicked, just close
                              // the dialog box and do nothing
                              dialog.cancel();
                          }
                      });
      
              // create alert dialog
              AlertDialog alertDialog = alertDialogBuilder.create();
      
              // show it
              alertDialog.show();
      
          }
      
      
      }
      

      //如果遇到任何问题,请告诉我

      方法 2

      或者在您的情况下,只需将此方法粘贴到您的主要活动中,这样您也可以实现您想要的:)
      @Override
      public void onBackPressed() {
          // TODO Auto-generated method stub
      
          AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(MainActivity.this);
      
          // set title
          alertDialogBuilder.setTitle("Exit");
      
          // set dialog message
          AlertDialog.Builder builder = alertDialogBuilder.setMessage("Do you really want to exit?").setCancelable(false)
                  .setPositiveButton("Yes", new DialogInterface.OnClickListener() {
                      public void onClick(DialogInterface dialog, int id) {
                          // if this button is clicked, close
                          // current activity
      
                          System.exit(0);
                      }
                  }).setNegativeButton("No", new DialogInterface.OnClickListener() {
                      public void onClick(DialogInterface dialog, int id) {
                          // if this button is clicked, just close
                          // the dialog box and do nothing
                          dialog.cancel();
                      }
                  });
      
          // create alert dialog
          AlertDialog alertDialog = alertDialogBuilder.create();
      
          // show it
          alertDialog.show();
      
      }
      

      【讨论】:

      • 你真的认为你的答案会解决 Shailesh 问题吗,因为他只想要一个警报,并且只有当片段 A 不显示其他片段并且你的代码会在所有片段上创建警报时。
      • 是的,在这种情况下,方法 1 适用于 shailesh,方法 2 适用于所有要跟踪的片段后退按钮,但如果我们在后退按钮被跟踪时传递一些条件,则方法 2 也更可取跨度>
      • 我猜方法 1 对他也不起作用。因为单击任何片段上的后退按钮会使 KEYCODE_BACK 的 if 条件始终为真。
      • 不,如果他将method1放在FragmentA中,它会起作用,因为method1我们可以放入任何特定的片段,我们可以跟踪该特定片段的点击。
      • 您不能覆盖Fragment 中的onKeyDown 方法。你知道吗?您只能在 Activity 中覆盖,就像在 Fragment 中无法覆盖的 onBackPressed 方法一样
      【解决方案4】:

      如果你想覆盖 onBack 按下的方法,然后在你的 onActivityCreated() 方法中添加这段代码

      getView().setFocusableInTouchMode(true);
              getView().requestFocus();
              getView().setOnKeyListener(new View.OnKeyListener() {
                  @Override
                  public boolean onKey(View v, int keyCode, KeyEvent event) {
                      if (keyCode == KeyEvent.KEYCODE_BACK) {
                            getFragmentManager().popBackStack();
                          return true;
                      }
                      return false;
                  }
              });
      

      【讨论】:

        【解决方案5】:

        使用下面的代码希望它有所帮助。

        //Always replace/add your fragment with a tag so that you can use that tag in future
        
             Fragment fr = getSupportFragmentManager().findFragmentByTag("Fragment_Name");//Fragment Name is a tag to identify fragment
             if (fr == null) {
             getSupportFragmentManager().beginTransaction()
             .replace(R.id.frame_container, new Demo_Fragment(), "Fragment_Name").commit();
             }
        
            //Now override onBackPressed method in MainActivity Only no need to do it in Fragment Class
            @Override
             public void onBackPressed() {
             Fragment fr = getSupportFragmentManager().findFragmentByTag("FragmentA");
            if(fr==null)
            //replace FragmentA
            else
            //Show Alert Box
             }
        

        【讨论】:

          【解决方案6】:

          为此,您需要执行以下操作

          在保存当前片段对象的 BaseFragment 或 Activity 上创建方法

           public void setCurrentFragment(Fragment currentFragment) {
                          this.currentFragment = currentFragment;
                         }
          

          并创建一个返回当前片段对象的方法

          public Fragment getCurrentFragment() {
                  return currentFragment;
              }
          

          现在只需要调用getCurrentFragment 方法并检查Fragment 是否是A 片段的实例

          if (getCurrentFragment() instanceof AFragment) {
                      showAlert
                  } else {
                      super.onBackPressed()
                  }
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2017-06-13
            • 1970-01-01
            • 1970-01-01
            • 2012-12-08
            相关资源
            最近更新 更多