3

Я получаю следующие отчеты об ошибках:Невозможно выполнить это действие после того, как onSaveInstanceState показать

Fatal Exception: java.lang.IllegalStateException: Не удается выполнить это действие после того, как onSaveInstanceState в android.support.v4 .app.FragmentManagerImpl.checkStateLoss (FragmentManager.java:1832) на android.support.v4.app.FragmentManagerImpl.enqueueAction (FragmentManager.java:1850) на android.support.v4.app.BackStackRecord.commitInternal (BackStackRecord.java : 643) на android.support.v4.app.BackStackRecord.commit (BackStackRecord.java:603) at android.support.v4.app.DialogFragment.show (DialogFragment.java:143)

Этот следующий код вызывает сбой, я вырезал некоторые тривиальный код установки для ясности. Я прочитал эту ошибку, и, насколько я понимаю, .show() должен быть безопасным в рамках взаимодействия с пользователем, например onClick(). Единственное, о чем я могу думать, это то, что query() занимает много времени, и пользователь своп. Это разумное объяснение этой ошибки? Это мгновенно на моих устройствах даже с большой БД. Любые другие возможности? Благодаря!

foldersButton.setOnClickListener(new View.OnClickListener() 
    { 
     @Override 
     public void onClick(View v) 
     { 
      final List<String> paths = new ArrayList<>(); 

      try(Cursor c = getActivity().getContentResolver().query(Meta.CONTENT_URI, 
        new String[]{"DISTINCT " + Meta.PARENT}, null, null, 
        Meta.PARENT + " ASC")) 
      { 
       while (c != null && c.moveToNext()) 
       { 
        String path = c.getString(c.getColumnIndex(Meta.PARENT)); 

        // We place the excluded folders at the end 
        if (!mExcludedFolders.contains(path)) 
         paths.add(path); 
       } 
      } 

      [setup...] 

      int[] position = new int[2]; 
      foldersButton.getLocationOnScreen(position); 
      FolderDialog dialog = FolderDialog.newInstance(
        paths.toArray(new String[paths.size()]), 
        visible, 
        excluded, 
        position[0], 
        position[1]); 
      dialog.setStyle(DialogFragment.STYLE_NO_TITLE, R.style.FolderDialog); 

      [setup...] 

      dialog.show(getFragmentManager(), TAG); 
     } 
    }); 
+0

У вас найдено решение для этого фатального исключения. – RameshJaga

ответ

0

Вы можете показать диалог прогресса, пока ваш запрос выполняется и сделать пользователь ждать на экране и в то же время сообщить ему, что что-то находится в процессе обработки.

Или если вы не хотите информировать пользователя об обработке в этом случае, проверьте, является ли действие порогом на переднем плане, а затем отобразите диалог.

Вы можете использовать одну логическую переменную isInForeground и установить/сбросить ее в onResume и соответственно.

@Override 
    protected void onPause() { 
     super.onPause(); 
     isInForeground=false; 
    } 

    @Override 
    protected void onResume() { 
     super.onResume(); 
     isInForeground=true; 
    } 

Затем обернуть диалоговое шоу логики, если условие

if(isInForeground){ 
    dialog.show(getFragmentManager(), TAG); 
} 
2

Если этот код ваш находится в деятельности, оберните призыв к show с:

if(!isDestroyed() && !isFinishing())

и если этот код находится внутри фрагмента, заверните вызов show с:

if (isResumed() && !isRemoving())

Это более или менее было бы решить вопрос о высадке в неустойчивом состоянии UI

0

Чем больше я смотрел на нее тем больше это беспокоит меня, что у меня был запрос в коде пользовательского интерфейса. Вероятно, это был мой первоначальный код, чтобы проверить концепцию, и я небрежно оставил ее, когда она сработала.

Для приложения используется LoaderManager, но я использовал существующий onLoadFinished, чтобы запустить асинхронный запрос, который будет обновлять структуру пути при любых изменениях в db. Теперь, когда пользователь щелкает, диалог готов к работе.

Поскольку я не могу воспроизвести ошибку, это будет неделя или около того, прежде чем я смогу сделать вердикт по этому вопросу, но в любом случае предыдущий код был неаккуратным.

0

Кажется, что ваша деятельность приостановлена ​​/ ваше приложение не находится в foregraound. Вы можете сделать одну вещь, прежде чем добавить проверку фрагмент ли ваша деятельность не уничтожается/отделки и ваше приложение находится на переднем плане (это не свернуто)

if(!isDestroyed()&&!isFinishing()&&isAppInForground(this)){ 
//add your fragment 
} 

Написать код, чтобы проверить ваше приложение находится на переднем плане или нет

/** 
     * 
     * @param context 
     * @return boolean 
     * tells whether user is currently viewing app or not if not return false otherwise true 
     */ 
     public static boolean isAppInForground(Context context){ 
      boolean isInForeground = false; 
      ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); 

       List<ActivityManager.RunningAppProcessInfo> runningProcesses = am.getRunningAppProcesses(); 
       for (ActivityManager.RunningAppProcessInfo processInfo : runningProcesses) { 
        if (processInfo.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) { 
         for (String activeProcess : processInfo.pkgList) { 
          if (activeProcess.equals(context.getPackageName())) { 
           isInForeground = true; 
          } 
         } 
        } 
       } 

      return isInForeground; 
     }