ビューにかなり大きなパスを描画していますが、パフォーマンスの問題が発生しています。パスの長さは現在32,000ポイントですが、私のアプリケーションは少なくとも128,000ポイントに拡張する必要があります。データセットが非常に大きいため、パスのサイズについては実際には何もできません。パス全体を一度に表示してズームインできるようにする必要があります。
Android4.2を実行しているNexus10を使用しています。これは、明示的に無効にしないアプリケーションに対して、デフォルトでハードウェアアクセラレーションが有効になっています。
パスは次のコードで作成されます(セットアップやその他の無関係な部分は省略しました)。
dataPath.moveTo(0, offset - (float) data[leftLimit]/ scalingFactor);
for (int i = leftLimit; i < rightLimit; ++i) {
x = (i - leftLimit) * dx;
y = offset - (float) data[i]/ scalingFactor;
dataPath.lineTo(x, y);
}
そして、onDraw()
メソッドで描画されます:
canvas.drawColor(Color.WHITE);
canvas.drawPath(dataPath, linePaint);
ハードウェアアクセラレーションを使用した場合と使用しない場合を使用してビューを描画するのにかかる時間を測定しましたがadb shell dumpsys gfxinfo
、驚いたことに、ハードウェアアクセラレーションははるかに遅いです。
ハードウェアアクセラレーションの場合:
ハードウェアアクセラレーションなし:
ハードウェアアクセラレーションバージョンは、フレームあたり約200〜300ミリ秒かかり、ほとんどがプロセス段階で費やされます。非加速バージョンは約50ミリ秒かかり、描画段階で2/3、プロセス段階で1/3になります。
明らかに、ハードウェアアクセラレーションのない高速バージョンでさえ、60 fpsを達成するには遅すぎるか、より大きなデータセットに移動するときにほとんど使用できません。
私の場合、ビットマップへのパスをレンダリングしてから、そのビットマップのみを画面に合わせて変換するというアイデアも問題があります。パスの非常に遠いズームインをサポートする必要があり、パスの品質を大幅に悪化させることなくズームインを有効にするには、パスの特大のビットマップをレンダリングする必要があります(メモリ制限とテクスチャサイズ制限に遭遇する可能性があります)。また、ズームインするときは、パスの一部のみの新しい画像を作成するか、パスを直接レンダリングするように切り替える必要があります。これにより、パフォーマンスが適切なものと同じである場合、フレームレートよりも大きな遅延が発生する可能性があります。今。
私が今疑問に思っているのは
- 線/パスの描画はGPUが得意ではないものであり、ハードウェアの高速化を試みるべきではありませんか、それともパフォーマンスの低下を引き起こす何か間違ったことをしている可能性がありますか?
- 許容できるパフォーマンスでこのような巨大なパスを描くために私にできることはありますか?