View.getWidth()
これは、メソッドとメソッドのスレッドセーフに関する簡単な質問View.getHeight()
です。
View オブジェクトを指定して操作を実行するバックグラウンド タスクを作成しています。実際に必要なビューの唯一の部分は、その寸法です。ただし、タスクが開始されたときにビューがレイアウト プロセスを経ていない可能性があるため、その寸法が 0 に設定されています。タスクは UI で開始されますが、バックグラウンドで長い操作が実行されてから、結果を投稿する UI スレッド ( によく似ていますAsyncTask
)。
バックグラウンド スレッドからこれらのゲッター メソッドを呼び出すと、どのような影響があるのだろうと考えていました。UI ツールキットがシングル スレッド用に設計されていることはわかっているため、安全でないパブリケーションのリスクを冒している可能性があります。
Kcoppock は、ディメンションがわかっているときに UI スレッドでコールバックを受け取ることによって、この問題をすべて回避する優れたソリューションを提供しています。
これらのディメンションがバックグラウンド スレッド (以下に添付) からいつ表示されるかを確認する小さなテストを書きましたが、コールバックと同時に利用できるようです。
もちろん、これが何の証明にもならないことは理解していますので、UI フレームワークについてより詳しい知識をお持ちの方に参加していただければ幸いです。
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
final ImageView view = new ImageView(this);
view.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
Log.d("TAG", Thread.currentThread().getName() + ": onGlobalLayout()");
Log.d("TAG", Thread.currentThread().getName() + ": view dimensions: " + view.getWidth() + "x" + view.getHeight());
}
});
// Bad code follows
new Thread(new Runnable() {
@Override
public void run() {
while (true) {
Log.d("TAG", Thread.currentThread().getName() + ": view dimensions: " + view.getWidth() + "x" + view.getHeight());
try {
Thread.sleep(1);
} catch (InterruptedException ignored) {}
}
}
}).start();
setContentView(view);
Log.v("TAG", "Set view as content");
}