UI 要素 (ビュー階層) は UI スレッドからのみ操作できることを知っています。バックグラウンド操作の場合、UI スレッドに到達するイベント ハンドラーを提供する AsyncTask を使用できます。
簡単に言うと、getApplicationContext()
UI 以外のスレッドでビュー (に関連付けられている) をインスタンス化することは許可されていますか? このカスタム ビューの子孫は、インスタンス化されると、UI スレッドからビュー階層に追加されます。したがって、コンストラクターの呼び出しのみがAsynctask.doInBackground()
;内で行われます。addView(...)
アクティビティのルート レイアウト階層へのアタッチ ( ) は、引き続き UI スレッドで行われます。
詳細に:
public MyView extends View {
public MyView(Context context) {
...
}
...
}
onDraw(...)
オーバーライドなどを使用して、カスタム ビューを作成しました。ユーザーがメイン アクティビティの特定の MenuItem をクリックすると、別のアクティビティ (MyOtherActivity) が作成されて表示されます。この画面はまさに MyView です。
MyOtherActivity の画面はすぐに表示する必要があるため、ユーザーがメイン アクティビティの別の場所にいる間 (つまり、その MenuItem をまだクリックしていないとき)、AsyncTask で MyView を事前にインスタンス化します。MyView 参照は、静的データ メンバーに格納されます。
が
MyOtherActivity.onCreate()
呼び出されると、そのコンストラクター コードは静的から MyView を取得し、それを を介してレイアウト ルート階層に追加しますaddView(...)
。(静的変数がメモリリークを引き起こす可能性があることは承知しているので、
null
不要になったら一度に設定します。)
MyView が別のスレッドでインスタンス化される (およびgetApplicationContext()
そのコンストラクターで戻り値を取る) ことは問題ではありませんか (予期しない問題が発生する可能性があります)。