Problem
OpenCVSharpのOpenCVSharp.Cv2.ImReadメソッドは、内部的には、OpenCVのcv::imread関数を呼んでいます。
問題は、OpenCVがユニコード文字列を扱えないため、ANSI文字列しか受け取れないことです。
より正確には、OpenCVSharpからネイティブに自動的にマーシャリングされる際に、System.String、つまりUTF-16からANSI文字列に変換されています。
その際、非ユニコードに変換できない文字列を含むと以下の例外を投げます。
マーシャリングできません: マップできない文字を検出しました。
UTF-16から、ANSIへのマーシャリングは、.NETのソースを見ると、System.String.ConvertToAnsiメソッドを経由し、WideCharToMultiByte関数が呼ばれています。
なので、どうしようもありません。
本当に?
Solution
問題は、下記にように、ファイルパスを渡しているから問題が起きるわけです。
1 | var mat = OpenCvSharp.Cv2.ImRead(filepath); |
つまり、下記のように、メモリデータを直接渡し、デコードすれば良いわけです。
1 | var array = File.ReadAllBytes(filepath); |
Cv2.ImDecodeの第2引数は指定が必須です。OpenCvSharp.Cv2.ImReadは本来第2引数がありますが、既定でImreadModes.Colorが設定されるので、同じ値にしておきました。