2012-03-05 7 views
6

방향 변경에 대한 내 응용 프로그램에서 이상한 동작이 있습니다.방향 변경 후 활동의 두 번째 인스턴스

정상 동작 : 내 응용 프로그램을 열 때
내 집 활동이 시작됩니다. 다음 액티비티 (갤러리)로 이동하면 정상적으로 시작됩니다 (오른쪽에서 왼쪽으로 슬라이딩 애니메이션이 있음). 뒤로 키를 사용하여 돌아 가면 현재 활동 (갤러리)이 완료됩니다 (왼쪽에서 오른쪽으로 슬라이드 아웃 애니메이션이 있음).

이상한 행동 : 내가 세로 모드에서 응용 프로그램을 시작하고 가로로 방향을 변경하고있어

  • . 그런 다음 가정 활동의 두 번째 사례와 같은 것이 있습니다. 왜냐하면 가로 모드에서 뒤로 버튼을 누르기 만하면 (예 : 홈 활동이 내 앱의 첫 번째 활동 인 경우) 오리엔테이션 변경이없는 것처럼 앱이 닫히지 않기 때문에 라헤 터는 왼쪽에서 오른쪽으로 슬라이딩 애니메이션을 만듭니다 (새 활동 시작) 그리고 집에있는 활동을 보여줍니다 (하지만 저는 또 다른 사례라고 생각합니다). 뒤로 버튼을 다시 누르면 응용 프로그램이 닫힙니다.
  • 가로 모드에서 앱을 시작하고 세로 모드로 변경하면 버튼을 누르면 오른쪽에서 왼쪽으로 슬라이드 애니메이션 (예 : 활동 닫기)이 표시되고 홈 활동이 다시 표시됩니다.
  • 앱을 시작하고 세로 방향으로 두 세로 방향 변경을하면 뒤로 버튼이 앱을 닫아야합니다.

그래서 풍경과 인물 모드는 두 가지 다른 활동처럼 취급됩니다.

오리엔테이션 변경은 정상적인 안드로이드 활동 라이프 사이클을 따라야하고 "오래된"초상화 (또는 가로) 버전의 활동을 파괴해야합니다.
내 활동은 FragmentActivity에서 상속됩니다. 나는 onSaveInstanceState을 사용하여 (활동에 대한 참조를 포함하지 않는) parceable을 전달하고 onRetainCustomNonConfigurationInstance (read here)을 사용하여 여러 개의 AsyncTask을 전달합니다. 그러나이 작업의 모든 참조는 onRetainCustomNonConfigurationInstance에서 삭제되고 getLastCustomNonConfigurationInstance 이후 복원됩니다 (새로 생성 된 활동 포함).

어떤 아이디어가이 동작을 일으킬 수 있습니까?

편집 : 매니페스트 파일에
활동 선언 :
<activity android:name=".activities.smartphone.HomeSmartphone" android:label="@string/app_name"></activity>

HomeSmartphone 집 확장이
홈 MyFragmentActivity
에게 MyFragmentActivity를 확장하는 것은

에서 android.support.v4.app.FragmentActivity를 확장 MyFragmentActivity 나는 onCreate, onRestart, onStart, onSaveInstanceState, onPause, onResu에서 몇 가지 로깅/추적 작업을 수행합니다. 나, onStop, onDestroy는 응용 프로그램 컨텍스트에 대한 참조 만 보유하고있는 추적 클래스의 정적 메서드를 호출합니다. 활동 컨텍스트가 아닙니다.

홈은 HomeSmartphone 및 HomeTablet에 의해 확장되는 추상 클래스입니다.이 두 클래스는 다른 레이아웃에서 일부 특수로드/새로 고침/초기화를 수행합니다.

대부분의 작업은 추상 홈 클래스에서 수행됩니다.



    public HomeRetainedObjects retained = new HomeRetainedObjects(); 

    public boolean adIsShown = false; 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     this.setContentView(R.layout.home); 

     Log.i("DEBUG", "onCreate(Home)"); 

     if (savedInstanceState != null) { 
      this.adIsShown = savedInstanceState.getBoolean("adIsShown"); 
     } 

    // write/update values in shared preferences 
     this.initPreferences(); 

    // recover retained objects (mostly AsyncTasks) 
     this.recoverRetained(); 

    // show content/refresh content 
     this.init(); 
    } 

    @Override 
    protected void onSaveInstanceState(Bundle outState) { 
     super.onSaveInstanceState(outState); 

     outState.putBoolean("adIsShown", this.adIsShown); 

     Log.i("DEBUG", "onSaveInstanceState(Home)"); 
    } 

    public void recoverRetained() { 
     Object retained = this.getLastCustomNonConfigurationInstance(); 
     if (retained instanceof HomeRetainedObjects) { 
      this.retained = (HomeRetainedObjects) retained; 

      if (this.retained.loadMessageTask != null) { 
       this.retained.loadMessageTask.restoreContext(this); 
      } 
     } 
    } 

    @Override 
    public Object onRetainCustomNonConfigurationInstance() { 
     if (this.retained.loadMessageTask != null) { 
      this.retained.loadMessageTask.destroyContext(); 
     } 

     return this.retained; 
    } 

이 정보가 도움이 되었기를 바랍니다.

+0

코드를 표시하십시오 ... –

+0

... 매니페스트, PLZ에 활동 선언이 포함되어 있습니다. – Turnsole

+3

+1 우리에게 당신의 노력을 보여주는 잘 제기 된 질문 :) –

답변

0

비슷한 문제가 발생하여 문제의 원인이 onRetainCustomNonConfigurationInstance()을 무시하고있는 것 같습니다.

보유 상태 개체를 검토 한 결과 Context에 대한 참조가있는 것으로 나타났습니다. 내가 WeakReference 래핑하고 정상적인 동작을 반환하고 이상한 이중 인스턴스에 대한 잔소리.

보존 상태가 Context에 대한 참조를 보유하고있을 가능성이 있습니까?