私はKinectとOpenCVを使用しています。私はすでにこのフォーラムで検索していますが、私の問題のようなものは見つかりませんでした。 Kinect(16ビット)からの生の深度データを保持し、それをCvMat *に保存してから、それをcvGetImageに渡して、そこからIplImage *を作成します。
CvMat* depthMetersMat = cvCreateMat( 480, 640, CV_16UC1 );
[...]
cvGetImage(depthMetersMat,temp);
しかし今、cvThreshdoldを実行して輪郭を見つけるために、この画像で作業する必要があります。これらの2つの関数は、入力に8ビット深度の画像を必要とします。 CvMat * depthMetersMatを8ビット深度-CvMat *に変換するにはどうすればよいですか?
@SSteveが出した答えはほとんど私にとってはうまくいきましたが、convertTo
の呼び出しは、実際に値を8ビット範囲にスケーリングするのではなく、上位バイトを切り落とすように見えました。 @Sirninoはどの動作が必要かを指定していなかったので、他の誰かがそれをしたい場合に備えて、(線形)スケーリングを行うコードを投稿すると思いました。
SSteveの元のコード:
CvMat* depthMetersMat = cvCreateMat( 480, 640, CV_16UC1 );
cv::Mat m2(depthMetersMat, true);
m2.convertTo(m2, CV_8U);
値をスケーリングするには、convertTo
の呼び出しの3番目のパラメーター(アルファ)としてスケール係数(1/256、または16ビットから8ビットのスケーリングの場合は0.00390625)を追加する必要があります。
m2.convertTo(m2, CV_8U, 0.00390625);
アルファを掛けた後に各値に追加される4番目のパラメーター(デルタ)を追加することもできます。詳細については、 docs を参照してください。
これは機能するはずです:
CvMat* depthMetersMat = cvCreateMat( 480, 640, CV_16UC1 );
cv::Mat m2(depthMetersMat, true);
m2.convertTo(m2, CV_8U);
しかし OpenCVのドキュメントによると 、CvMatは廃止されました。代わりにマットを使用する必要があります。