更新履歴
2019/08/20 第1版 H2MD / H2MD for Unity ドキュメント統合 初版
2019/10/21 第2版 サウンド同期のサンプルをrequestAnimationFrameに変更
2019/12/06 第3版 H2MD_WebGL.premultipliedAlpha APIを追加
2020/05/26 第4版 体裁や文言の見直し、 request(callback)を削除、 「3.8. リクエストコールバックの利用」を削除

1.概要

1.1 H2MD とは

H2MDは、ブラウザとネイティブアプリの両方に対応した動画再生ミドルウェアです。αチャンネルの活用や柔軟なシーク、自動再生、複数同時再生を行うことができます。また、フレーム間予測によりJPEG連番フォーマットであるMotionJPEGを超える圧縮率を実現します。

1.2 SDKの内容

H2MD SDK は、H2MDを使用したアプリケーションを開発するためのソフトウェアスイートです。H2MD SDK には以下が含まれます

項目 概要 対応ファイル
コマンドラインエンコーダ 動画から H2MD ストリームファイルに変換するためのツールです。 Windows およびMac に対応しています。 tools/x86/h2md_enc_c.exe
tools/x64/h2md_enc_c.exe
tools/mac/h2md_enc_c
プレーヤ H2MD ストリームファイルを再生するためのツールです。WindowsおよびMacに対応しています。 tools/x86/amplay.exe
tools/mac/amplay.dmg
ライブラリ C++やC#およびJavaScriptでH2MDストリームファイルを再生するためのライブラリです。 library/include
library/[PLATFROM]
サンプル C++とJavaScriptでH2MDストリームファイルを再生するためのサンプルです。 samples/
Unity Plugin Unity でH2MDストリームファイル を再生するためのライブラリです。 unity/
PlayCanvas Plugin PlayCanvas でH2MDストリームファイル を再生するためのライブラリです。 playcanvas/

1.3 ネイティブライブラリの対応プラットフォーム

H2MDのデコードライブラリは以下をターゲットとしてビルドしています。

OS ビルドターゲット デコードライブラリ名 ライブラリビルド環境
Windows Windows 7 以降 h2md_dec.dll VS2015
Mac macOS 10.13以降 libh2md_dec.dylib Xcode
Android Android 4.4以降 libh2md_dec-STL.a(*)
libh2md_dec-STL.so(*)
Android NDK (r10e, r19c)
iOS iOS 9.0以降 h2md_dec-VER.a(*) Xcode

(*)VERにはバージョン番号、STLには使用するSTLの名称が入ります。

1.4 JavaScript版ライブラリの動作確認済みのブラウザ

JavaScript版ライブラリの動作確認済ブラウザは以下となります。

OS ブラウザ
Windows 7 IE11 , Chrome33
Windows 10 Edge , Chrome76
Mac Chrome76
Android 4.4 標準ブラウザ , Chrome33
Android 8.1 Chrome77
iOS 11 Safari

※上記以外のブラウザでも随時動作を確認しています。詳細はお問い合わせください

2. H2MDストリームファイルの作成と確認

2.1 H2MDストリームの形式

H2MDストリームには、エンコード後のH2MDストリームが単体ファイルとなるパック形式と、エンコード後のH2MDストリームが複数ファイルで構成されるアンパック形式の2種類があります。

パック形式(デフォルト) アンパック形式
ブラウザでのデコード 対応 対応
ブラウザでのストリーミング 非対応 対応
ブラウザでのクロスドメイン再生 非対応 対応(JSONPオプション利用時)
h2md_view.jsでの再生 対応 対応
ネイティブアプリでのデコード 対応 非対応
Unityでのデコード 対応 非対応
amplay(プレーヤ)でのデコード 対応 非対応


パック形式はブラウザとネイティブアプリの両方で使用可能です。パック形式では以下のようなファイルが出力されます。

アンパック形式はブラウザでのみ使用可能です。アンパック形式では、以下のようなファイルが出力されます。

通常はパック形式を使用し、ブラウザでストリーミングしたい場合や、クロスドメイン対応を行いたい場合にアンパック形式を使用してください。

2.2 H2MD エンコーダ

H2MDエンコーダを使えば、任意の動画ファイルから H2MDストリームファイルに変換することができます。Windowsの場合「コマンドプロンプト」や「Windows PowerShell」、MacOSの場合、「ターミナル」などのコマンドラインアプリケーションを立ち上げ、実行することができます。

入力ファイル名と、出力ファイル名、画質を次のように与えると、エンコードが行われ、out.h2md が出力されます。

h2md_enc_c -i in.avi -o out.h2md -q 75

コマンドライン引数に-a オプションを与えることで、アルファチャンネル付きでエンコードすることもできます。

h2md_enc_c -i in.avi -o out.h2md -q 75 -a 4

コマンドライン引数に--unpackオプションを与えることで、アンパック形式でエンコードすることができます。

h2md_enc_c -i in.avi -o out.h2md -q 75 --unpack

コマンドライン引数に--unpackオプションと同時に、-fオプションを与えることで、エンコード結果をフォルダにまとめることができます。(下記例ではエンコード結果を「out」フォルダに保存)

h2md_enc_c -i in.avi -o out.h2md -q 75 --unpack -f out

2.3 コマンドラインオプション

オプション 機能
--input , -i 入力ファイルを指定します。AVI などの動画ファイルや連番 BMP フォルダなどが指定可能です。エンコード可能な最大解像度は、4096 x 4096 です
--output , -o 出力ファイルを指定します。 拡張子は h2md にして下さい。
--folder, -f 出力先フォルダを指定します。 フォルダが存在しない場合はフォルダを作成します。
--quality , -q RGB チャンネルの品質を 0~100 で指定します。大きいほど高画質です。 デフォルト値は 50です。
--alpha_bit , -a アルファチャンネルのビット数を 0~8 で指定します。大きいほど高画質です。 アルファチャンネルが不要な場合は 0 を指定して下さい。デフォルト値は 0 です。
--block_size , -b 動画のブロックサイズを 8、16、32、64 で指定することができます。 大きいほどデコード速度は向上しますが、主観画質が低下します。 デフォルト値は 16 です。
--fps フレームレートを設定します。 大きいほど滑らかになりますが、デコード負荷が上がります。 デフォルトでは入力ファイルのフレームレートを使用します。
--gop_frames GOP を挿入する間隔を指定します。0 を指定するとシーンチェンジに合わせて自動的にGOPを挿入します。 デフォルト値は 0 です。
--gop_list GOP を挿入するフレームをリストファイルで指定します。
--frames エンコードするフレーム数を指定します。 動画の最初から一部だけをエンコードする場合に指定します。
--resize_w 入力画像の幅を設定のピクセルに拡縮します。 割合(--resize_ratio_w, --resize_ratio_h)と同時には設定できません。
--resize_h 入力画像の高さを設定のピクセルに拡縮します。 割合(--resize_ratio_w, --resize_ratio_h)と同時には設定できません。
--resize_ratio_w 入力画像の幅を設定の割合(%単位)に拡縮します。 ピクセル(--resize_ w, --resize _h)と同時には設定できません。
--resize_ratio_h 入力画像の高さを設定の割合(%単位)に拡縮します。 ピクセル(--resize_ w, --resize_ h)と同時には設定できません。
--keep_aspect 幅または高さの設定を基準に、縦横比を保ちながら拡縮します。 幅と高さが両方設定されている場合、当オプションは設定できません。
--intra_size 内部イントラ画像サイズをピクセル単位で設定します。デフォルトは1024です。 ターゲットとなるデバイスのJPEGデコーダの制約を満たす必要があります。
--syntax_size シンタックスデータの出力データサイズをKバイト単位で設定します。デフォルトは256です。4の倍数を設定する必要があります。
--unpack アンパック形式でデータを書き出します。(ドキュメント2.1項参照)
--jsonp シンタックスデータを、.b64 ファイルではなく.js ファイルに書き出します。 クロスドメイン制約に対応する必要がある場合に使用します。 --unpackを設定する必要があります。
--b64 --jsonp設定時に追加で設定することで.b64ファイルも同時に書き出します。
--psy-rd 符号量よりも主観画質を優先してエンコードします。
--robust 通信の最適化による影響を低減する形式でエンコードします。 ファイルサイズが増加しますが、通信の最適化による再圧縮時のノイズを低減します。

2.4 GOPリストの入力

指定したフレームへのシークを高速化したい場合、該当フレームをGOP挿入フレームとすることで実現可能です。GOPリストを入力することで、GOP挿入フレームを任意に指定することができます。

h2md_enc_c -i in.mp4 -o out.h2md --gop_list gop_list.txt

gop_list.txtには、以下のように、GOP を挿入するフレーム番号を行単位で記述します。この例では、0 フレームと 10 フレームに GOP を設定します。GOP を設定したフレームは基準フレームとなり、フレームデータの圧縮率は低下します。

0
10

2.5 H2MDプレーヤアプリでのプレビュー

パック形式のH2MDストリームファイルは、H2MDプレーヤアプリで画質を確認することができます。

Windowsでの確認方法

1. tools/x86/amplay.exe を実行し、「AxMediaPlayer」を起動します。
2. ファイルメニューから「開く」をクリックして、パック形式のH2MDファイルを開きます。

3. 画面下部にある再生ボタンをクリックします。再生中は、再生ボタンが一時停止ボタンに変化します。スライドバーで任意のフレームに移動できます。


Macでの確認方法

初回のみインストール(手順1、2)を行います。

1. tools/mac/Amplay_release_**.dmg を開きます。(**には番号が入ります)

2. 「Amplay」のアイコンを「アプリケーションフォルダ」にドロップして、インストールします。

3. アプリケーションウィンドウで、Amplay を開きます。



4. ファイルメニューから「開く」をクリックして、パック形式のH2MDファイルを開きます。


5. 画面下部にある再生ボタンをクリックします。再生中は、再生ボタンが一時停止ボタンに変化します。スライドバーで任意のフレームに移動できます。

2.6 ブラウザでのプレビュー

h2md_view.jsを使用することで、ブラウザ上でH2MDストリームファイルの画質を確認することができます。ブラウザでのプレビューには、tools/js/h2md_view.htmlをブラウザで開き、再生したいH2MDストリームファイルをウィンドウにドロップします。

例えば、sample/js/movie_unpacked/にある以下のアンパック形式のH2MDストリームファイルをエクスプローラで選択します。

tools/js/h2md_view.htmlを開いているブラウザにドロップすると、H2MDストリームファイルを再生することができます。下記の画像で、左側は berserker.h2md.*.*、右側はbg.h2md.*.*の再生時のものです。

2.7 パフォーマンスの最適化

H2MDのデコードで十分なパフォーマンスが出ない場合は、--block_size 32を指定してエンコードしてください。デフォルトの--block_size 16に比べて、おおよそ4倍のパフォーマンスを得ることができます。ただし、ブロックノイズが目立ちやすくなります。逆に、デフォルトの設定でブロックノイズが目立つ場合は、--block_size 8を指定することで、デコードのパフォーマンスは低下しますが、ブロックノイズを目立ちにくくすることもできます。

2.8 通信の最適化への対応

ここでの「通信の最適化」とは、通信中に発生する JPEG ファイル等の再圧縮を指します。 再圧縮により、H2MD ストリームファイル中の JPEG ファイル等が変化すると、デコード結果に影響が出る場合があります。例えば、空などの画像でブロックノイズが目立つようになるなどです。 このような場合は、--robust オプションを指定してエンコードすることで、通信の最適化による影響を低減させる形式にできます。ただし、圧縮率が低下します。

2.9 動画ファイルの読み込みでエラーが発生する場合

Windows版のH2MDエンコーダでは、動画ファイルの読み込みにDirect Showを使用しています。mp4の読み込みでエラーが発生する場合には、Haali Media Splitterなど、mp4に対応したSplitterをインストールする必要があります。 Mac版のH2MDエンコーダでは、動画ファイルの読み込みにFFMPEGを使用しています。mp4の読み込みでエラーが発生する場合には、FFMPEGをインストールする必要があります。FFMPEGがインストールされているかどうかは、コマンドラインでffmpegと入力することで確認することができます。

3. JavsScript API

3.1 プロジェクトへのインポート

library/jsフォルダにあるh2md.min.jsを読み込んで下さい。
クロスドメイン制約から、h2md.min.jsと動画ファイルは同じドメインに存在する必要があります。

3.2 API仕様

H2MDインスタンスは次のAPIを持ちます。

再生制御API
API 引数 返値 説明
open(url,callback) url : String

callback : Function()
- urlからアンパック形式のH2MDストリームファイルを開きます。成功した場合は引数に与えたコールバックを、失敗した場合はerror APIで指定したコールバックを呼び出します。openしたインスタンスを別の動画で再利用することはできません。
open_packed(data,callback) url : String

callback : Function()
- urlからパック形式のH2MDストリームファイルを開きます。成功した場合は引数に与えたコールバックを、失敗した場合はerror APIで指定したコールバックを呼び出します。openしたインスタンスを別の動画で再利用することはできません。
open_mem(data,callback) data : Uint8Array

callback : Function()
- dataからH2MDストリームを開きます。成功した場合は引数に与えたコールバックを、失敗した場合はerror APIで指定したコールバックを呼び出します。openしたインスタンスを別の動画で再利用することはできません。
close() - - リソースを解放します。通常はGCによってリソースが解放されますが、明示的にWebGLのリソースを解放したい場合に使用します。
play() - 成功時はtrue、
失敗時はfalse
H2MDストリームを再生します。再生に失敗した場合はfalseを返します。再生中に内部エラーが発生した場合は、error APIで指定したコールバックを呼び出します。
stop() - - 再生を停止します。
pause() - - 再生を一時停止します。
clear() - - 再生画面をクリアします。
seek(frame) frame : Number 成功時はtrue、失敗時はfalse 指定したフレーム番号にシークします。
playing() - 再生中はtrue、再生していない場合はfalse 再生しているかどうかを取得します。
info() - Info H2MDストリームの動画情報をオブジェクトで取得します。openに成功した後に呼び出すことができます。失敗した場合はnullを返します。
position() - Position H2MDストリームの再生位置をオブジェクトで取得します。openに成功した後に呼び出すことができます。失敗した場合はnullを返します。
再生設定API
API 引数 返値 説明
canvas(canvas_id) canvas_id : String 成功時はtrue、
失敗時はfalse
デコード結果描画先キャンバスID、もしくはキャンバスオブジェクトを指定します。
stretch(dx,dy,dw,dh) dx : Number
dy : Number
dw : Number
dh : Number
- デコード結果描画先キャンバスにおける描画先座標と描画サイズを指定します。デフォルトでは(dx,dy)=(0,0)、(dw,dh)=(movie_width,movie_height)となります。
loop(loop_frame) loop_frame : Number 成功時はtrue、失敗時はfalse ループ再生時のループ先のフレーム番号を指定します。-1を指定するとループしません。デフォルト値は-1です。
streaming(flag) flag : Boolean - falseに設定するとプログレッシブダウンロードで再生します。trueに設定するとストリーミングで再生します。デフォルトはfalseです。
コールバック設定API
API 引数 返値 説明
error(callback) callback : Function(error_message:String) - エラー発生時に呼び出すコールバックを指定します。
done(callback) callback : Function() - 最後のフレームまで再生が終了したタイミングで呼び出すコールバックを指定します。
buffered(callback) callback : Function() - 全フレームのデータの読み込みが完了したタイミングで呼び出すコールバックを指定します。
timeupdate(callback) callback : Function() - 再生位置が更新されたタイミングで呼び出すコールバックを指定します。
キャッシュ制御API
API 引数 返値 説明
nonce_url(nonce) nonce : Boolean - trueに設定することで、画像のリクエストURLにタイムスタンプを付加し、キャッシュを無効化します。デフォルト値はfalseです。
JSONP API
API 引数 返値 説明
jsonp(jsonp) jsonp : Boolean - trueに設定することで、JSONPを使用してデータを読み込みます。エンコード時に—jsonpオプションを使用して、シンタックスデータを、.b64 ファイルではなく .js ファイルに書き出す必要があります。また、エンコード後のファイル名は、ページ内でユニークである必要があります。
ローレベルAPI
API 引数 返値 説明
decode(frame) frame : Number Canvas 引数に与えたフレームの画像をデコードしてCanvasオブジェクトで返します。読み込みが完了していないフレーム番号が指定された場合はnullを返します。返値のCanvasオブジェクトは内部バッファへの参照となり、再利用されるため、破壊してはいけません。また、別のdecode命令を実行すると、Canvasオブジェクトの内容は変化します。
コンポジットAPI
API 引数 返値 説明
compositeOperation(operation) operation : string - composite APIで合成する際の合成モードを指定します。source-over、copy、lighterの3モードが指定可能です。
compositeTransform(m11,m12,m21,m22,dx,dy) m11, m12, m21, m22 : Number
dx, dy : Number
- composite APIで合成する際の変換行列を指定します。変換行列はcomposite APIで指定する描画先の座標に対して適用されます。
compositeColor(r,g,b,a) r,g,b,a : Number - composite APIで合成する際の頂点カラーを指定します。値は0~1.0で指定します。H2MD_WebGL.directCompositeを使用しない場合はα値のみ有効です。
composite(frame,sx,sy,sw,sh,dx,dy,dw,dh) frame : Number
sx, sy, sw, sh : Number
dx, dy, dw, dh : Number
- 引数に与えたフレームの画像をデコードしてcanvas APIに指定したCanvasに描画します。(sx,sy)を始点として(sw,sh)のサイズの領域を、(dx,dy)を始点として(dw,dh)のサイズの領域に描画します。
WebGL API
API 引数 返値 説明
H2MD_WebGL.directComposite(enable) enable : boolean - trueに設定するとワークCanvasを経由せずに直接、フレームバッファにレンダリングします。
H2MD_WebGL.premultipliedAlpha(enable) enable : boolean - trueに設定するとH2MDファイルを乗算済みアルファモードでレンダリングします。
H2MD_WebGL.setWebGLEnable(enable) enable : boolean - trueに設定するとブラウザに依存せず強制的にWebGLを有効化します。falseに設定するとブラウザに依存せず強制的にWebGLを無効化します。

Infoオブジェクトは次のメンバを持ちます。

メンバ 概要
width 画像の横幅
height 画像の高さ
image_format イメージタイプ H2MDDEC_IMGFMT_*定数
frames 総フレーム数
fps_numerator 分数表現したフレームレート(フレーム毎秒)の分子
fps_denominator 分数表現したフレームレート(フレーム毎秒)の分母
fps フレームレート
caps H2MDDEC_MOVIE_CAPS定数のビット単位論理和

Positionオブジェクトは次のメンバを持ちます。

メンバ 概要
frames 総フレーム数
current_frame 現在の再生フレーム
buffered_frame バッファリングの完了したフレーム数

3.3 URLからH2MDストリームを再生する

まず、H2MDのインスタンスを作成します。

instance=new H2MD ();

次に、URLからH2MDストリームファイルを開きます。第一引数にはH2MDストリームファイルのURLを指定します。第二引数には、成功時に呼び出されるコールバックを指定します。

アンパック形式の場合は、URLには.h2md以降の数値と拡張子を除いた形式で指定します。

instance.open("out.h2md",success_callback);

パック形式の場合は、以下のように指定します。

instance.open_packed("out.h2md",success_callback);

open APIまたは open_packed APIに成功した後、play APIで任意のキャンバスで再生することができます。

instance.canvas("canvas_id");
instance.play();

フレーム番号を指定して直接、デコード画像を取得することもできます。取得したcanvas_objectはHTML5のdrawImage APIで描画することができます。取得した画像は32ピクセルの倍数にパディングされますので、必要に応じてクリップしてください。

canvas_object=instance.decode(frame);

3.4 メモリからH2MDストリームを再生する

まず、URLから動画データを取得します。

var req = new XMLHttpRequest();
req.open('get', "out.h2md", true);
req.responseType="arraybuffer";
req.onload = function(ev) {
var h2md_data= new Uint8Array(req.response);
};
req.send(null);

H2MDストリームの取得が完了したら、デコーダインスタンスを作成します。第一引数には取得したH2MDストリームの格納場所を指定します。第二引数には、成功時に呼び出されるコールバックを指定します。

instance=new H2MD ();
instance.open(h2md_data,success_callback);

open_mem APIに成功した後、play APIで任意のキャンバスで再生することができます。

instance.canvas("canvas_id");
instance.play();

3.5 エラー処理

エラー発生時に呼び出すコールバックを指定するには、error APIでコールバックを設定します。

instance.error(function (error){alert(error);});

3.6 情報の取得

フレーム数などの情報はinfo APIでオブジェクトの形式で取得することができます。

info=instance.info();
var width=info.width;

再生位置などの情報はposition APIでオブジェクトの形式で取得することができます。

position=instance.position();
var frame=position.current_frame;

H2MDストリームの動画情報のみを取得したい場合、静的関数を使用することもできます。シンタックスデータのみをサーバから読み込むため高速です。

H2MD.info_from_uri("out.h2md",
function(info){ /* info.width */ },
function(message){ /* error message */ }
);

3.7 プログレッシブダウンロードとストリーミング

プログレッシブダウンロードは、圧縮データを先頭から順次読み込み、デコーダにキャッシュする再生方法です。プログレッシブダウンロードは、短い動画や、ループ再生、過去へのシークが発生するコンテンツに最適です。また、複数ストリーム間でのフレーム同期が必要で、buffered APIを使用する場合にも、プログレッシブダウンロードを使用する必要があります。

ストリーミングは、圧縮データを必要なフレームから読み込み、デコードが完了したフレームの圧縮データはキャッシュせずに削除する再生方法です。ストリーミングは、長い動画や、メモリの少ない環境に最適です。

H2MDは、デフォルトではプログレッシブダウンロードを使用します。ストリーミングに設定する場合は、以下のように、open APIの前にstreaming APIを呼び出してください。

instance.streaming(true);
instance.open("out.h2md",success_callback);

3.8 クロスドメインでの動画再生

エンコード時に--unpackと--jsonpを指定することで、クロスドメインでH2MDストリームを再生することができます。

instance.jsonp(true);
instance.open("out.h2md",success_callback);

3.9 WebGLによるアクセラレーション

h2md.min.jsを読み込む前に、h2md.webgl.min.jsを読み込ませることで、WebGLによるアクセラレーションが有効になります。

<script type="text/javascript" src="../library/js/h2md.webgl.min.js"></script>
<script type="text/javascript" src="../library/js/h2md.min.js"></script>

WebGLによるアクセラレーションを有効にすると、PCとAndroidのGoogle Chromeでは、大きくデコード速度が改善します。iOSやFirefoxでは、逆にデコード速度が低下するため、現状、Google Chromeの場合のみ、アクセラレーションが有効になります。
強制的にアクセラレーションを有効にするには、H2MD_WebGL.setWebGLEnable(true)を実行して下さい。
WebGLを使用した場合は、クロスドメイン制約により、画像を同一ドメインに配置する必要があります。

3.10 Composite APIの活用

H2MDでは、通常、1つの動画につき1つのCanvasを対応付けます。ゲームのように複数の動画を1つのCanvasに対応付ける場合、Composite APIを使用します。以下の例では、1つのCanvasに対して、2つの動画をデコードし、描画しています。

h2md_a.canvas("canvas_id");
h2md_b.canvas("canvas_id");
h2md_a.composite(frame_idx,0,0,128,128,0,0,128,128);
h2md_b.compositeOperation(“lighter”);
h2md_b.composite(frame_idx,0,0,128,128,0,0,128,128);      

WebGLを使用する場合、H2MD_WebGL.directComposite(true)を実行することで、ワークCanvasを経由しない高速な合成が可能になります。ただし、directCompositeを有効にした状態では、ブラウザが確保できるwebgl-contextの上限を超える数のCanvasを扱うことはできません。

3.11 Composite Transform APIの活用

compositeTransform APIを使用することで、composite APIの描画先座標に対して行列変換を適用することができます。行列変換において、回転の原点を動画の中心座標にするには、composite APIの描画先座標にオフセットを追加し、行列変換の適用座標の重心が動画の中心になるようにします。

composite(node._playingFrame,0,0,info.width,info.height,-info.width/2,-info.height/2,info.width,info.height);

dx,dyを起点に描画を行う場合は、以下を与えます。最初に与えたオフセットを復元します。

compositeTransform(1,0,0,1,dx+info.width/2,dy+info.height/2);

画像の中心を原点に回転を行う場合は、以下の回転行列を適用します。

var c=Math.cos(theta)
var s=Math.sin(theta)
compositeTransform(c,s,-s,c,dx+info.width/2,dy+info.height/2);

画像の中心を原点に拡大を行う場合は、以下の拡大行列を適用します。

compositeTransform(scale,0,0,scale,dx+info.width/2,dy+info.height/2);

3.12 Cocos2d との併用

cocos2dと併用する場合、H2MDの内部で書き換えたシェーダを、cocos2dのシェーダに復帰させる必要があります。具体的に、H2MDのcomposite APIを呼び出した後、以下の命令によってシェーダを復帰して下さい。シェーダの復帰方法はcocos2dのバージョンによって異なる場合があります。

cc._currentShaderProgram=-1;
cc._blendingSource = -1;
cc._blendingDest = -1;

3.13 音声との同期

H2MDには音声データは含まれていませんが、audio要素などの再生位置を取得することで、簡単に同期再生することができます。次の例では、audio要素を再生しながら、定期的にcurrentTimeを取得し、現在の時間に対応したH2MDのフレームをデコードし、描画しています。



3.14 サンプルプログラム

sampleフォルダのjs/sample_*.htmlのJavaScriptコードを参照してください。sample_*.htmlでは、../library/jsフォルダのh2md.min.jsとh2md.webgl.min.jsを参照します。

4. C++ API

4.1 C++ APIとは

C++ APIを使用すると、C++を使用してH2MDストリームファイルをデコードすることができます。

4.2 インタフェース定義のinclude

includeフォルダにあるh2md_dec.hをincludeします。

4.3 ライブラリのWindowsプロジェクトへのインポート

windowsフォルダにあるh2md_dec.libをアプリケーションにリンクします。windows/[x86, x64]フォルダにあるh2md_dec.dllをアプリケーションと同じフォルダに置きます。

4.4 ライブラリのMacプロジェクトへのインポート

macフォルダにあるh2md_dec.dylibをアプリケーションにリンクします。h2md_dec.dylib をアプリケーションがライブラリを検出できる場所(ライブラリ検索パス等)に配置します。

4.5 ライブラリのiOSプロジェクトへのインポート

以下のライブラリをXcodeにドロップします。

ライブラリ C++ Standard Library Enable Bitcode
ios/h2md_dec-VER.a(*) libc++ 対応

(*)VERにはバージョン番号が入ります。

H2MDストリームファイルはXcodeのSupportingFilesに登録します。

4.6 ライブラリのAndroid NDKプロジェクトへのインポート

Android フォルダのサブフォルダにあるlibh2md_dec-STL.aをアプリケーションにリンクします。(「STL」には使用するSTLの名称が入ります。)
サブフォルダの意味は以下のとおりです。
・android/arm64-v8a : ARM 64bit用
・android/armeabi-v7a : ARM 32bit用
・android/x86 : x86 32bit用


各ライブラリのビルド設定は以下になります。

ライブラリ APP_PLATFORM APP_STL APP_CPPFLAGS
android/[arm64-v8a, armeabi-v7a, x86] /libh2md_dec-gnustl_static.a android-9 gnustl_static -fexception
android/[arm64-v8a, armeabi-v7a, x86] /libh2md_dec-stlport_static.a android-9 stlport_static -fexception
android/[arm64-v8a, armeabi-v7a, x86] /libh2md_dec-c++_static.a android-16 c++_static -fexception

Application.mkには以下のような記述を行って下さい。API-LEVEL 9以上が必要です。

APP_OPTIM := release
APP_ABI := armeabi-v7a
APP_PLATFORM := android-9
APP_STL := gnustl_static

Android.mkには以下のような記述を行って下さい。

LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
ARMEABI := armeabi-v7a
LOCAL_MODULE := libh2md_dec-st
LOCAL_SRC_FILES := ../../static_lib_dec/obj/local/$(ARMEABI)/libh2md_dec.a
include $(PREBUILT_STATIC_LIBRARY)
include $(CLEAR_VARS)
LOCAL_CFLAGS += -DANDROID -DNDEBUG
LOCAL_CPPFLAGS += -I ../../../../export -fvisibility=hidden
LOCAL_CPPFLAGS += -fexceptions
LOCAL_MODULE := libh2md_dec
LOCAL_ARM_MODE := arm
LOCAL_ARM_MODE := thumb
LOCAL_SRC_FILES += jni.cpp main.cpp
LOCAL_LDLIBS := -lm -lz -llog -ldl -ljnigraphics -lEGL -lGLESv1_CM -lGLESv2
LOCAL_STATIC_LIBRARIES := cpufeatures libh2md_dec-st
include $(BUILD_SHARED_LIBRARY)
$(call import-module,cpufeatures)

AndroidNDK r19c以降を使用する場合は$(call import-module,cpufeatures)を$(call import-module,android/cpufeatures)に置き換えてください。

4.7 デコードサンプル

次の例では、iOSリソースのsample.h2mdからアセットへのパスを取得します。

#include “h2md_dec.h”
NSString *path=[[NSBundle mainBundle] pathForResource:@”sample” ofType:@”h2md”];

//デコーダインスタンスを作成
struct H2MDDecoder *decoder;
h2mdCreate(&decoder,H2MDDEC_IMAGE_BGRA,1);

//H2MDストリームを開く
int ret=h2mdOpenStreamFileA(decoder, [path cStringUsingEncoding:1]);

if(ret!=H2MDDEC_STATUS_SUCCESS){
	printf("ERROR CODE: %d",ret);
	return -1;
}

//H2MDストリームの動画情報を取得する
H2MDMovieInfo movie_info;
ret=h2mdGetMovieInfo(decoder,&movie_info,H2MDDEC_MOVIE_INFO_VERSION);

//デコード先メモリを確保
std::vector<unsigned char> rgbquad(movie_info.width*movie_info.height*4);

//全フレームデコードする
for(int frame=0 ; frame < movie_info.total_frames ; frame++){
	//デコード
	h2mdDecode(decoder,frame);
	//デコード結果画像の取得
	h2mdGetImage(decoder,&rgbquad[0],rgbquad.size(),movie_info.width*4);
	//ここに取得したRGBQUADデータをBMPに書き込む等の処理を入れてください
}
//デコーダインスタンスを破棄する
h2mdDestroy(decoder);

4.8 サンプルプログラム

C++ APIのサンプルプログラムsample/h2md_sample_decode.cppを参照して下さい。

5. Unityプラグイン

5.1 概要

H2MDに同梱されているUnity Pluginを使用すると、Unity5以降でH2MDストリームファイルを使用したコンテンツを作成することができます。Unity Pluginで作成したコンテンツは、iOS、Android、Windows、Mac、WebGLへの書き出しに対応しています。

5.2 プロジェクトへのインポート

UnityフォルダのUnityパッケージをインポートするか、Unity/Assetsの一式をUnityのプロジェクトにコピーしてください。Pluginsフォルダにバイナリが、AXIP/H2MD/ScriptsフォルダにC#の定義ファイルがあります。

5.3 UnityPackageのフォルダ構成

UnityPackageにはH2MDのUnity Pluginとサンプルシーンが含まれます。UnityPackageはUnity 2017.4.30f1でビルドされています。Samplesフォルダ以下はサンプルでのみ使用するリソースとなりますので、最終アプリに含める必要はありません。

フォルダ名 内容
AXIP/H2MD/Samples/Scenes サンプルシーンが格納されています。
AXIP/H2MD/Samples/Materials サンプルで使用するマテリアルが格納されています。
AXIP/H2MD/Scripts H2MDのAPIが格納されています。
AXIP/H2MD/Editor ビルド時に-lzフラグを付加するスクリプトが格納されています。
Plugins H2MDのNative Pluginが格納されています。
StreamingAssets/H2MD サンプルで使用する動画素材が格納されています。
WebGLTemplates/H2MDTemplate WebGL書き出しで使用するテンプレートが格納されています。

5.4 H2MDストリームファイルのインポート

Unity/Assets/StreamingAssetsフォルダにH2MDストリームファイルをコピーしてください。

5.5 プレーンへのアタッチ

任意のプレーンにH2MDTexture.csをドロップしてください。InspectorのPathにH2MDストリームファイルへのパスを設定してください。PathにはStreamingAssetsを除いたファイル名を指定します。

5.6 uGUIへのアタッチ

任意のuGUIのRawImageにH2MDTexture.csをドロップして下さい。
InspectorのPathにH2MDファイルへのパスを設定して下さい。
Flipにチェックを入れて下さい。必要に応じてPreviewにチェックを入れて下さい。

5.7 プロジェクトの実行

再生ボタンを押すと、H2MDストリームファイルが再生されます

5.8 API仕様

H2MD for UnityのAPIは以下の3階層になっています。API の詳細は、各 cs ファイルに記載していますので、ご参照ください。

クラス 概要
H2MDDecoder H2MD の低レべル API。
H2MDMovie H2MDDecoderクラスを使用してH2MDストリームファイルを開き、Textureを返す。フレーム番号を指定して、Textureにデコードする。
H2MDTexture H2MDMovie クラスを使用して Unity のオブジェクトに動画をアタッチする。

5.9 データ読み込みの内部動作

Windows、Mac、iOSの場合は、StreamingAssetsから標準ファイルAPIでデータを読み込みます。AndroidとWebGLの場合は、wwwクラスでStreamingAssetsのデータを読み込みます。H2MDTextureのifdefを書き換えることで、Windows、Mac、iOSでもwwwクラスを使用してデータを読み込むように変更することもできます。また、AndroidやWebGLでもpersistentDataPathにデータをコピーすることで、標準ファイルAPIを使用することもできます。

5.10 iOS への書き出し

Unity 5.3からzlibの扱いが変更になったため、Unity 5.3以降でビルドする場合、 XcodeのOther Linker Flagsに-lzを追加する必要があります。なお、Editor/PostBuildProcessH2MD.csをプロジェクトに登録することで、-lzの追加を自動化することができます。

5.11 リンクエラーへの対策

iOSおよびAndroidでリンクエラーが発生する場合、以下の二点を確認して下さい。

1. iOSでScripting BackendにMonoを指定している場合、_h2mdOpenStreamFileでリンクエラーが発生することがあります。その場合、Scripting BackendをIL2CPPに指定してください。Monoで動作させる必要がある場合はH2MDDecoder.csを書き換えることで、_h2mdOpenStreamFileAを直接呼び出してください。

2. Pluginをインポートした際、Plugins/[x86,x86_64]/h2md_decをInspectorで参照すると、Any Platformに設定されている場合があります。その場合、Any Platformのチェックを外し、Exclude PlatformsがInclude Platformsに変わったのを確認して、Include PlatformsをEditor + Standaloneに設定してください。

5.11 WebGLへの書き出し

WebGLで書き出したアプリケーションの実行にはh2md.min.jsが必要です。WebGLへの書き出し後にhtmlファイルを書き換えることでh2md.min.jsを読み込ませるか、Player Settingsにおいて、同梱のWebGLTemplatesを使用して下さい。

6. PlayCanvas Plugin

6.1 概要

H2MDに同梱されているPlayCanvas Pluginを使用すると、PlayCanvasでα付きH2MDストリームファイルを扱うことができます。

6.2 プロジェクトへのライブラリのインポート

library/js/h2md.min.js、playcanvas/H2MDTexture.js、パック形式のH2MDストリームファイルをプロジェクトに登録します。

6.3 H2MDTextureの利用

オブジェクトにH2MDTexture.jsを設定し、videoUrlにH2MDストリームファイルへのパスと、materialsにデコード先のマテリアルを設定します。

実行すると、マテリアルのEmissiveおよびAlphaにデコードした画像が転送されます。

7.ライセンス

7.1. エンコーダ

H2MDエンコーダが使用しているAxMediaLoader.dllおよびlibAxMediaLoader.dylibではOpenEXRを使用しています。

Copyright (c) 2002-2011, Industrial Light & Magic, a division of Lucasfilm Entertainment Company Ltd. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. Neither the name of Industrial Light & Magic nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.


H2MDエンコーダが使用しているlibAxMediaLoader.dylibではlibpngおよびlibjpegを使用しています。

this software is based in part on the work of the Independent JPEG Group

7.2 プレーヤ

Windows版のamplayはMs-PLでライセンスされたnaudioを使用しています。

7.3 デコードライブラリ

H2MDのネイティブデコードライブラリではlibjpegもしくはlibjpeg-turboとlibpngを使用しています

this software is based in part on the work of the Independent JPEG Group