仅在完成活动时显示PopupWindow

时间:2018-09-05 19:49:03

标签: java android

当用户赢得我的游戏时,我试图在SurfaceView的顶部显示PopupWindow 5秒钟。 MainThread用于处理游戏循环。

使用我的代码,当游戏获胜时,它会暂停5秒钟,并且在活动结束时会快速显示PopupWindow。 为了更准确地将PopupWindow显示在:

gActivity.finish();

代替:

popupWindow.showAtLocation(this, Gravity.NO_GRAVITY, 0, 0);

我该怎么办?

这是我的代码:

public class GamePanel extends SurfaceView implements SurfaceHolder.Callback {
  private MainThread thread;   // MainThread extends Thread

  ...

    if (gameWon) {

          thread.setRunning(false);
          thread.drawAndUpdate();
          popWellDoneWindow();

          Intent returnIntent = new Intent();
          returnIntent.putExtra("result", true);

          Activity gActivity = (Activity) (this.getContext());
          gActivity.setResult(Activity.RESULT_OK, returnIntent);
          gActivity.finish();
    }

  ...


  public void popWellDoneWindow() {

     LayoutInflater layoutInflater = (LayoutInflater)(getContext().getApplicationContext().getSystemService(LAYOUT_INFLATER_SERVICE));
     ViewGroup popupView = (ViewGroup)layoutInflater.inflate(R.layout.well_done, null);

     PopupWindow popupWindow = new PopupWindow(popupView, Constants.SCREEN_WIDTH, Constants.SCREEN_HEIGHT, false);
     popupWindow.showAtLocation(this, Gravity.NO_GRAVITY, 0, 0);

     try {
         Thread.sleep(5000);
     }
     catch (InterruptedException ie){
         ie.printStackTrace();
     }
  }

}

public class GameActivity extends AppCompatActivity {

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(new GamePanel((GameActivity)this, (int) getIntent().getSerializableExtra("LevelNumber")));
  }

}

1 个答案:

答案 0 :(得分:0)

查看the source code的PopupWindow.java,它将视图添加到WindowManager。

调用WindowManager#addView()时,不会同步添加它;即,该方法可以在实际添加View之前,期间或之后返回。但是它仍然在主线程上进行添加。所以有问题的代码是

Thread.sleep(5000);

您是在调用运行WindowManager#addView()的方法之后立即调用该方法,这意味着该方法在添加View之前返回,并且当前线程停止了5秒钟,从而阻止了该线程的实际添加。

使用处理程序代替Thread.sleep()

Handler handler = new Handler();
handler.postDelayed(new Runnable() {
    @Override
    public void run() {
        ((Activity) GamePanel.this.getContext()).finish();
    }
}, 5000);

这将在5秒钟后调用Activity的finish()方法,而不会阻塞主线程。