拡張ビューのonDraw()にLog.d()呼び出しを配置したため、呼び出しの頻度とタイミングを確認できました。ビューのインスタンス化時に呼び出されますが、これは驚くことではありません。しかし、気付いたのですが、onTouchEvent()によって処理されるすべてのタップで呼び出されます。ただし、私のコードはグラフィックに関連するリモート処理を行っていません。ただし、Viewsの documentation では、onDraw()が実際に呼び出されるタイミングについては何も見つけられないようです。私はここで特定のプロジェクトを心配していません(これは私にとって問題を引き起こしません)、私はどこかにリストがあるかどうか、またはビューの操作の順序を示す何か、特に原因を知りたいですonDraw()が呼び出されます。
AFAIK、ビューのonDraw()は次の場合に呼び出されます:
無効化は、必要に応じてユーザーまたはシステムから呼び出すことができます。たとえば、多くのビューは、アウトラインとカーソルを取得するEditTextや、押された状態のボタンなど、Touchの外観を変更します。このため、ビューはタッチで再描画されます。
Viewsの動作を詳しく説明したドキュメントがあればいいと思います。もし存在し、誰かがそれを見つける場所を知っているなら、私たちに知らせてください。
onDraw()
が呼び出されると、invalidate()
が呼び出されます。
ただし、ViewGroupsについては知っておく必要があります:onDraw()
は呼び出されません。むしろ、onDispatchDraw()
。
ただし、ViewGroupでは、コンストラクターでsetWillNotDraw(false)
を呼び出して、onDraw()
をinvalidate()
で呼び出すことができます。
この答え を見てください
ビューに描画可能な背景を設定すると、ビューはonDraw()メソッドをコールバックする前にそれを描画します。
onAttachedToWindow()は、ビューがウィンドウにアタッチされるときに呼び出されます。この時点で、Surfaceがあり、描画を開始します。この関数は、onDraw(Android.graphics.Canvas)の前に呼び出されることが保証されていますが、onMeasure(int、int)の前後を含め、最初のonDrawの前であればいつでも呼び出すことができます。
invalidate()は、ダーティによって定義される領域を描画する必要があるとしてマークします。ビューが表示されている場合、onDraw(Android.graphics.Canvas)は将来のある時点で呼び出されます。
覚えておくべき重要なことは、引数なしでinvalidate()関数の呼び出しを最小限に抑えることです。代わりに、4つの引数でinvalidate()関数を最大化してみてください。ビュー全体の描画は非常にコストがかかるため、2番目のバリアントはビューの一部のみを更新します。
上記に加えて、ソフトキーボードは、 'キーボード'を適切に収容するためにウィンドウのサイズを変更した後、View.invalidate()-> View.onDraw()シーケンスを発生させます。カスタムView.onDraw()は、この可能性を予測する状態のままにする必要があります。
このような現象は、Bluetoothキーボードを搭載したタブレットで開発およびテストしたアプリが、現実世界に到達すると犬に伝わる理由を説明しています(-: