ohos-dev-graphics-pixel-tests-generator について
ohos-dev-graphics-pixel-tests-generator は、OpenHarmony Rosen のグラフィックスピクセル比較フレームワーク向け C++ テストを作成する開発スキルです。既存コードの規約、描画ノードのライフサイクル、ビルド設定の更新を重視します。
主な機能
- 01描画内容に応じたテスト配置と種別の選択
- 02近接するテストファイルのパターンへの準拠
- 03描画ノードのライフタイム維持登録
- 04新規テスト用 BUILD.gn の更新
- 05マクロ、API、ビルド登録の確認
活用シーン
- 01グラフィックス属性のピクセル比較テスト作成
- 02アニメーションやエフェクトのテスト追加
- 03新しい C++ テストファイルのビルド設定
- 04空のスクリーンショットやビルド対象外の調査
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ openharmonyinsight/ openharmony-skills --skill ohos-dev-graphics-pixel-tests-generatorインストール後、Claude Code で/ohos-dev-graphics-pixel-tests-generatorを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
evals/evals.jsonREADME.mdreferences/code-patterns.mdframework-lifecycle.mdtemplates.mdtest-taxonomy-build.md詳細
OpenHarmony グラフィックピクセルテスト
このスキルを使用して、OpenHarmony Rosen グラフィックピクセル比較フレームワーク向けに、リポジトリのスタイルに沿った C++ テストを生成します。対象ディレクトリは通常、graphic_test/test です。
テストケースの生成は、テスト関数を一つ書くだけではありません。適切な結果にするには、正しいテストディレクトリと RSGraphicTestType を選び、隣接ファイルのスタイルに従い、フレームワークのライフサイクルを正しく使用し、保持が必要なレンダリングノードをすべて登録したうえで、新しい .cpp を追加する場合は graphic_test/test/BUILD.gn も更新する必要があります。
重要な禁止事項
GetRootNode()->AddChild(...)、AddChildToSubWindow(...)を呼び出した後、またはカスタム surface を作成した後にRegisterNode(...)を呼び忘れないでください。ノードが早期に解放され、スクリーンショットが空白になったり、不安定になったりする可能性があります。- 独立したテストを誤って
GRAPHIC_TESTSにしないでください。同じ fixture の複数のテスト surface を一枚のグリッドスクリーンショットにまとめる必要が明確にある場合に限り、これを使用します。 - 通常のグラフィックテスト用に新しい
ohos_unittestターゲットを作成しないでください。新しい.cppは、graphic_test/test/BUILD.gnにある既存の分類別 sources 配列に追加してください。 - Drawing の helper、テスト用 helper、RenderService API をでっち上げないでください。まず、隣接ファイルとフレームワークのヘッダーファイルを確認してください。
- 自動スクリーンショットテストに
FlushImplicitTransactionと sleep を安易に追加しないでください。手動スクリーンショットを撮る場合、レンダリング結果をすぐに照会する場合、または隣接テストで必要な場合に限り追加します。 - 存在が保証されない画像リソースのパスを使用しないでください。同じディレクトリにある
/data/local/tmp/...のパスを再利用するか、コード内で PixelMap を生成してください。
開始手順
- ワークスペース内で、実際の
graphic_testルートディレクトリを特定します。 - まず
graphic_test/graphic_test_framework/include/rs_graphic_test.hとrs_graphic_test_ext.hを読み、次に要件に最も近い既存のテストファイルを読みます。 - 生成する前に、次の確認事項に回答します。
- Purpose:検証する具体的なレンダリング動作またはスクリーンショットの差異は何ですか?
- Existing:既存のテストファイルを拡張すべきですか、それとも新規作成が適切ですか?
- Type:このシナリオに対応する
RSGraphicTestTypeとテストマクロは何ですか? - Pixels:スクリーンショットの差異を視認しやすく、安定して示すには、どの色、画像、枠線、グリッド、境界値を使いますか?
- Build:ファイルを新規作成する場合、
test/BUILD.gnのどの sources 配列に追加しますか?
- シナリオを確認した後、このスキル内の関連する参考ファイルのみを読みます。
references/framework-lifecycle.md:フレームワークのライフサイクル、マクロ、スクリーンショット、ノードのライフサイクル。references/test-taxonomy-build.md:テストの配置場所とtest/BUILD.gnの更新ルール。references/code-patterns.md:ノード、画像、Canvas、アニメーション、手動スクリーンショット、サブウィンドウ、PixelMap の一般的な書き方。references/templates.md:簡潔な開始用テンプレート。
- ローカルの隣接ファイルのスタイルを優先して踏襲します。参考ファイルはパターンを説明するものです。include、helper 名、API の使用可否については、既存コードを正とします。
- 少なくともテキストレベルの確認を行います。マクロ名、namespace、include、
RegisterNode、source list への追加、および架空の API がないことを確認します。
生成手順
1. テストの分類を判断する
テスト対象の動作に応じて、ディレクトリと RSGraphicTestType を選択します。
| シナリオ | よく使われるディレクトリ | よく使われるタイプ |
|---|---|---|
| ノードの外観、背景、前景、ジオメトリ、コンテンツ表示 | rs_display_effect/property_display または rs_display_effect/content_display | CONTENT_DISPLAY_TEST |
| アニメーションプロトコル、カーブ、カスタム modifier アニメーション | rs_display_effect/animation | ANIMATION_TEST |
| NG shader/filter/effect/mask/shape の視覚効果 | rs_effect_feature/... | EFFECT_TEST |
| PixelMap、font、symbol などのオープン機能 API | open_capability/... | 通常は CONTENT_DISPLAY_TEST。またはローカルの既存タイプを踏襲 |
| ダーティリージョン、HWC、GPU composer、hybrid render、パフォーマンス関連のレンダリング | rs_perform_feature/... | ローカルの既存タイプを踏襲。よく使われるのは CONTENT_DISPLAY_TEST、GPU_COMPOSER_TEST、HYBRID_RENDER_TEST |
| surface capture、screen capture、マルチスクリーン、アクセシビリティ、ウォーターマーク、render group | rs_func_feature/... | 通常は CONTENT_DISPLAY_TEST |
| フレームワークの surface 動作 | rs_framework/... | 通常は CONTENT_DISPLAY_TEST |
| Effect Kit NDK filter | effect_kit/... | EFFECT_TEST |
関連するファイルがすでにある場合は、そのファイルの拡張を優先します。機能の境界が明確で、追記すると既存ファイルが分かりにくくなる場合に限り、新しいファイルを作成します。
2. テストマクロを選択する
- 通常の自動スクリーンショットピクセルテストには、
GRAPHIC_TEST(TestClass, TYPE, TestName)を使用します。 GRAPHIC_TEST(TYPE, TestName)は、デフォルトの fixture を使うごく小規模なテストにのみ適しています。実際のテストファイルの多くでは、派生 fixture を定義します。- 複数のテスト関数を一枚のグリッドスクリーンショットにまとめる場合は、
GRAPHIC_TESTSを使用します。共有のSetScreenSizeを維持し、出力ファイル名に個々の test name が含まれないことに注意してください。 - スクリーンショットのタイミングを手動で制御する必要がある場合、カスタム
TestCaseCaptureを呼び出す場合、FlushImplicitTransactionの後に sleep する場合、または自動スクリーンショットを避ける必要がある場合に限り、GRAPHIC_N_TESTを使用します。 - タスクで録画/再生が明確に必要とされていない限り、
GRAPHIC_D_TESTは使用しないでください。現在のテストコードでは、自動テストと手動テストが主に使われています。
3. fixture を構築する
ほとんどのファイルでは、次のような構造を使用します。
class ExampleTest : public RSGraphicTest {
public:
void BeforeEach() override
{
SetScreenSize(screenWidth, screenHeight);
}
private:
const int screenWidth = 1200;
const int screenHeight = 2000;
};
サブ領域のキャプチャや全画面表示の動作を意図的にテストする場合に限り、SetSurfaceBounds を使用します。特殊なディスプレイのスクリーンショット、サブウィンドウ、手動スクリーンショットに関わる場合は、同じ機能領域の既存ファイルを参照してください。
4. 視認しやすく、再現性のあるピクセル出力を作成する
ピクセル比較テストでは、明確で安定した画面が必要です。
- テストでクリッピングや範囲外の動作を検証する場合を除き、ノードは設定済みの画面範囲内に配置します。
- パラメーターの組み合わせにはグリッドレイアウトを使用します。
screenWidth、screenHeight、行数と列数に基づいて、sizeX、sizeY、x、yを計算します。 - 期待される差異が視認できるよう、コントラストの強い背景、枠線、画像コンテンツを使用します。
- プロパティのクランプをテストする場合は、負数、0、中間値、1、大きな値、無効な列挙値などの境界値を含めます。
- 各値について個別の画像を生成する必要がある場合は、複数の
GRAPHIC_TESTを使用します。値を一枚のスクリーンショットで比較する必要がある場合は、単一テスト内にグリッドを作成します。
5. ノードを正しく追加し、保持する
シーンに追加してレンダリングする必要がある各ノードは、次のように処理します。
GetRootNode()->AddChild(testNode);
RegisterNode(testNode);
親子ノードツリーでは、親または子のローカル変数がスコープを抜ける可能性がある場合、親と子の両方を登録します。サブウィンドウでは、GetRootNode()->AddChildToSubWindow(subId, node) で追加し、引き続き RegisterNode(node) を呼び出します。
6. 必要な場合にのみ flush する
通常、自動テストでは TearDown() で flush とスクリーンショットをまとめて処理します。レンダリング結果をすぐに照会する必要がある場合、手動スクリーンショットを撮る場合、ノードを送信した後に surface/PixelMap API を呼び出す場合、または隣接テストですでに明示的な送信方式を採用している場合に限り、RSTransactionProxy::GetInstance()->FlushImplicitTransaction() を追加します。
FlushImplicitTransaction を使用する場合は、transaction/rs_interfaces.h を include する必要があります。
7. 新增文件时更新 BUILD.gn
新增 .cpp 时,必须更新 graphic_test/test/BUILD.gn,把相对路径插入匹配的 sources 数组,例如 rs_display_effect_sources、rs_effect_feature_sources、open_capability_sources、rs_func_feature_sources、rs_perform_feature_sources、rs_framework_sources 或 effect_kit_sources。
普通 graphic test 不要新建 ohos_unittest target。现有 RSGraphicTest target 已经汇总各分类 sources 数组。
完成前必要检查
声称完成前,至少运行快速文本检查:
rg -n "GRAPHIC_(N_)?TESTS?|RegisterNode|FlushImplicitTransaction" path/to/new_or_changed.cpp
rg -n "relative/path/to/new_file.cpp" graphic_test/test/BUILD.gn
然后确认:
- 文件有与相邻测试一致的 Apache copyright header。
- include 与实际 API 使用匹配,没有残留模板垃圾。
- 代码位于
namespace OHOS::Rosen。 - 每个测试宏都使用正确 fixture、类型和唯一测试名。
- 每个需要渲染的场景节点都已加入 root 或 sub-window,并调用
RegisterNode。 - 手动截图测试在 flush/wait 后调用截图 helper,并使用
GRAPHIC_N_TEST。 - 新文件已加入正确的 source array。
- 没有残留占位调用,例如
DrawTextBlob(...)、paintSetColor或虚构 helper 名称。
常见失败模式
| 失败现象 | 原因 | 修复 |
|---|---|---|
| 截图空白 | 节点未添加、未注册或没有可见属性 | 添加 child,调用 RegisterNode,设置可见 bounds/color/image |
| Drawing 代码编译失败 | 使用了泛化 Drawing API 签名,没有贴合本地风格 | 查看相邻 Drawing 测试,使用 Brush/Pen 和 AttachBrush/DetachBrush |
| 测试未参与构建 | 新 .cpp 没加到 test/BUILD.gn 分类数组 | 把相对路径加入正确 sources list |
| 输出分组错误 | 独立用例误用了 GRAPHIC_TESTS | 除非明确需要网格聚合,否则使用 GRAPHIC_TEST |
| 自动截图前特殊查询存在竞态 | 查询渲染输出前没有提交事务 | 添加 FlushImplicitTransaction,并参考相邻测试的等待模式 |
| 依赖资源的测试渲染为空 | 设备上缺少图片路径 | 复用同目录已有 /data/local/tmp/... 路径,或在代码中生成 PixelMap 数据 |
当前语料特点
当前 graphic_test/test 以 GRAPHIC_TEST 自动截图为主;GRAPHIC_N_TEST 大量用于脏区、surface、screen、水印和手动截图流程。GRAPHIC_TESTS 主要出现在 test_template 风格的网格聚合场景,应谨慎选择。
多数视觉属性测试不会在 C++ 中断言像素值,而是创建确定性的渲染场景,由框架把 PNG 保存到 /data/local/graphic_test/... 后再做比对。