From 40150505128066eb6fff2c4132bef55f4daacb7e Mon Sep 17 00:00:00 2001 From: Peter Rekdal Sunde Date: Wed, 12 Aug 2015 14:42:30 +0200 Subject: [PATCH 1/5] Optimize motion detector by using BitmapMat for Bitmap^ only. --- .../openalpr-net/motiondetector-net.cpp | 32 +++++++------------ 1 file changed, 12 insertions(+), 20 deletions(-) diff --git a/src/bindings/csharp/openalpr-net/motiondetector-net.cpp b/src/bindings/csharp/openalpr-net/motiondetector-net.cpp index 63721e9..18b9ed6 100644 --- a/src/bindings/csharp/openalpr-net/motiondetector-net.cpp +++ b/src/bindings/csharp/openalpr-net/motiondetector-net.cpp @@ -14,23 +14,20 @@ void AlprMotionDetectionNet::ResetMotionDetection(Bitmap^ bitmap) void AlprMotionDetectionNet::ResetMotionDetection(String^ filename) { - BitmapMat^ wrapper = gcnew BitmapMat(filename); - ResetMotionDetection(wrapper->Value); - delete wrapper; + cv::Mat mat = cv::imread(marshal_as(filename)); + ResetMotionDetection(mat); } void AlprMotionDetectionNet::ResetMotionDetection(MemoryStream^ memoryStream) { - BitmapMat^ wrapper = gcnew BitmapMat(memoryStream); - ResetMotionDetection(wrapper->Value); - delete wrapper; + return ResetMotionDetection(memoryStream->ToArray()); } void AlprMotionDetectionNet::ResetMotionDetection(array^ byteArray) { - BitmapMat^ wrapper = gcnew BitmapMat(byteArray); - ResetMotionDetection(wrapper->Value); - delete wrapper; + std::vector buffer = AlprHelper::ToVector(byteArray); + cv::Mat mat = cv::imdecode(buffer, 1); + ResetMotionDetection(mat); } System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(Bitmap^ bitmap) @@ -43,26 +40,21 @@ System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(Bitmap^ bitmap) System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(String^ filename) { - BitmapMat^ wrapper = gcnew BitmapMat(filename); - System::Drawing::Rectangle motion = MotionDetect(wrapper->Value); - delete wrapper; + cv::Mat mat = cv::imread(marshal_as(filename)); + System::Drawing::Rectangle motion = MotionDetect(mat); return motion; } System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(MemoryStream^ memoryStream) { - BitmapMat^ wrapper = gcnew BitmapMat(memoryStream); - System::Drawing::Rectangle motion = MotionDetect(wrapper->Value); - delete wrapper; - return motion; + return MotionDetect(memoryStream->ToArray()); } System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(array^ byteArray) { - BitmapMat^ wrapper = gcnew BitmapMat(byteArray); - System::Drawing::Rectangle motion = MotionDetect(wrapper->Value); - delete wrapper; - return motion; + std::vector buffer = AlprHelper::ToVector(byteArray); + cv::Mat mat = cv::imdecode(buffer, 1); + return MotionDetect(mat); } void AlprMotionDetectionNet::ResetMotionDetection(cv::Mat mat) From cd1c55c8b0b8ebd9a9c401c56b10a07fb9ad9e77 Mon Sep 17 00:00:00 2001 From: Peter Rekdal Sunde Date: Wed, 12 Aug 2015 15:41:32 +0200 Subject: [PATCH 2/5] Cleanup BitmapNet class. --- .../csharp/openalpr-net/bitmapmat-net.cpp | 26 +++++-- .../csharp/openalpr-net/bitmapmat-net.h | 69 ++----------------- 2 files changed, 27 insertions(+), 68 deletions(-) diff --git a/src/bindings/csharp/openalpr-net/bitmapmat-net.cpp b/src/bindings/csharp/openalpr-net/bitmapmat-net.cpp index 69db8f7..ba0d669 100644 --- a/src/bindings/csharp/openalpr-net/bitmapmat-net.cpp +++ b/src/bindings/csharp/openalpr-net/bitmapmat-net.cpp @@ -5,23 +5,37 @@ using namespace openalprnet; BitmapMat::BitmapMat(array^ byteArray) { - this->m_bitmap = ByteArrayToMat(byteArray); + m_bitmap = new cv::Mat(); + std::vector buffer = AlprHelper::ToVector(byteArray); + cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR, this->m_bitmap); } BitmapMat::BitmapMat(Bitmap^ bitmap) { - this->m_bitmap = BitmapToMat(bitmap); + m_bitmap = new cv::Mat(); + + MemoryStream^ ms = gcnew MemoryStream(); + bitmap->Save(ms, ImageFormat::Png); + + std::vector buffer = AlprHelper::ToVector(ms->ToArray()); + cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR, this->m_bitmap); + + delete ms; } BitmapMat::BitmapMat(MemoryStream^ memoryStream) { - this->m_bitmap = MemoryStreamBitmapToMat(memoryStream); + m_bitmap = new cv::Mat(); + std::vector buffer = AlprHelper::ToVector(memoryStream->ToArray()); + cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR, this->m_bitmap); } BitmapMat::BitmapMat(String^ filename) { - Bitmap^ bitmap = gcnew Bitmap(filename); - this->m_bitmap = BitmapToMat(bitmap); - delete bitmap; + m_bitmap = new cv::Mat(); + array^ byteArray = File::ReadAllBytes(filename); + std::vector buffer = AlprHelper::ToVector(byteArray); + cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR, this->m_bitmap); + delete byteArray; } diff --git a/src/bindings/csharp/openalpr-net/bitmapmat-net.h b/src/bindings/csharp/openalpr-net/bitmapmat-net.h index cedbf94..3732759 100644 --- a/src/bindings/csharp/openalpr-net/bitmapmat-net.h +++ b/src/bindings/csharp/openalpr-net/bitmapmat-net.h @@ -1,6 +1,9 @@ #pragma once -#include "opencv2/imgproc/imgproc.hpp" +#include +#include + +#include "helper-net.h" using namespace System; using namespace System::Drawing; @@ -33,74 +36,16 @@ namespace openalprnet { !BitmapMat() { - delete[] m_bitmap->data; + m_bitmap->release(); + delete m_bitmap; } property cv::Mat Value { cv::Mat get() { - cv::Mat value = this->m_bitmap->clone(); - return value; + return *m_bitmap; } } - private: - - static cv::Mat* BitmapToMat(Bitmap^ bitmap) - { - int channels = 0; - - switch (bitmap->PixelFormat) - { - case PixelFormat::Format8bppIndexed: - case PixelFormat::Format1bppIndexed: - channels = 1; - break; - case PixelFormat::Format24bppRgb: - channels = 3; - break; - case PixelFormat::Format32bppRgb: - case PixelFormat::Format32bppArgb: - case PixelFormat::Format32bppPArgb: - channels = 4; - break; - default: - throw gcnew NotSupportedException(bitmap->PixelFormat.ToString()); - } - - BitmapData^ bitmapData = bitmap->LockBits( - System::Drawing::Rectangle(0, 0, bitmap->Width, bitmap->Height), - ImageLockMode::ReadOnly, - bitmap->PixelFormat - ); - - const int totalBytes = bitmap->Height * bitmapData->Stride; - - char *dst = new char[totalBytes]; - ::memcpy(dst, bitmapData->Scan0.ToPointer(), totalBytes); - - cv::Mat* dstMat = new cv::Mat(cv::Size(bitmap->Width, bitmap->Height), CV_8UC(channels), dst); - - bitmap->UnlockBits(bitmapData); - - return dstMat; - } - - static cv::Mat* MemoryStreamBitmapToMat(MemoryStream^ memoryStream) - { - Bitmap^ bitmap = gcnew Bitmap(memoryStream); - cv::Mat* mat = BitmapToMat(bitmap); - delete bitmap; - return mat; - } - - static cv::Mat* ByteArrayToMat(array^ byteArray) - { - MemoryStream^ ms = gcnew MemoryStream(byteArray); - cv::Mat* mat = MemoryStreamBitmapToMat(ms); - delete ms; - return mat; - } - }; } \ No newline at end of file From b8f625bed0f594da881adad1c9e7037115e34e6f Mon Sep 17 00:00:00 2001 From: Peter Rekdal Sunde Date: Wed, 12 Aug 2015 15:42:39 +0200 Subject: [PATCH 3/5] Use overload. --- src/bindings/csharp/openalpr-net/openalpr-net.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/bindings/csharp/openalpr-net/openalpr-net.cpp b/src/bindings/csharp/openalpr-net/openalpr-net.cpp index d1519c9..b3bfa37 100644 --- a/src/bindings/csharp/openalpr-net/openalpr-net.cpp +++ b/src/bindings/csharp/openalpr-net/openalpr-net.cpp @@ -361,8 +361,7 @@ namespace openalprnet { /// Recognize from an image on disk /// AlprResultsNet^ Recognize(System::String^ filepath) { - AlprResults results = m_Impl->recognize(marshal_as(filepath)); - return gcnew AlprResultsNet(results); + return Recognize(filepath, gcnew List()); } /// From 6cfb804ad088fdb60a9ddffbcba3f95510c17a8a Mon Sep 17 00:00:00 2001 From: Peter Rekdal Sunde Date: Wed, 12 Aug 2015 15:42:00 +0200 Subject: [PATCH 4/5] Remove cli namespace. --- src/bindings/csharp/openalpr-net/openalpr-net.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/bindings/csharp/openalpr-net/openalpr-net.cpp b/src/bindings/csharp/openalpr-net/openalpr-net.cpp index b3bfa37..4ec0d66 100644 --- a/src/bindings/csharp/openalpr-net/openalpr-net.cpp +++ b/src/bindings/csharp/openalpr-net/openalpr-net.cpp @@ -418,7 +418,7 @@ namespace openalprnet { /// Recognize from byte data representing an encoded image (e.g., BMP, PNG, JPG, GIF etc). /// /// Bytes representing image data - AlprResultsNet^ Recognize(cli::array^ imageBuffer) { + AlprResultsNet^ Recognize(array^ imageBuffer) { return Recognize(imageBuffer, gcnew List()); } @@ -426,7 +426,7 @@ namespace openalprnet { /// Recognize from byte data representing an encoded image (e.g., BMP, PNG, JPG, GIF etc). /// /// Bytes representing image data - AlprResultsNet^ Recognize(cli::array^ imageBuffer, List^ regionsOfInterest) { + AlprResultsNet^ Recognize(array^ imageBuffer, List^ regionsOfInterest) { std::vector buffer = AlprHelper::ToVector(imageBuffer); std::vector rois = AlprHelper::ToVector(regionsOfInterest); AlprResults results = m_Impl->recognize(buffer, rois); @@ -436,14 +436,14 @@ namespace openalprnet { /// /// Recognize from raw pixel data /// - AlprResultsNet^ Recognize(cli::array^ imageBuffer, int bytesPerPixel, int imgWidth, int imgHeight) { + AlprResultsNet^ Recognize(array^ imageBuffer, int bytesPerPixel, int imgWidth, int imgHeight) { return Recognize(imageBuffer, bytesPerPixel, imgWidth, imgHeight, gcnew List()); } /// /// Recognize from raw pixel data /// - AlprResultsNet^ Recognize(cli::array^ imageBuffer, int bytesPerPixel, int imgWidth, int imgHeight, List^ regionsOfInterest) { + AlprResultsNet^ Recognize(array^ imageBuffer, int bytesPerPixel, int imgWidth, int imgHeight, List^ regionsOfInterest) { unsigned char* p = AlprHelper::ToCharPtr(imageBuffer); std::vector rois = AlprHelper::ToVector(regionsOfInterest); AlprResults results = m_Impl->recognize(p, bytesPerPixel, imgWidth, imgHeight, rois); From bdcd318ffe6c4b4c2230fa8a00972e272f9eb4f6 Mon Sep 17 00:00:00 2001 From: Peter Rekdal Sunde Date: Wed, 12 Aug 2015 15:57:18 +0200 Subject: [PATCH 5/5] Use enum value. --- src/bindings/csharp/openalpr-net/motiondetector-net.cpp | 4 ++-- src/bindings/csharp/openalpr-net/openalpr-net.cpp | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/bindings/csharp/openalpr-net/motiondetector-net.cpp b/src/bindings/csharp/openalpr-net/motiondetector-net.cpp index 18b9ed6..a9a716b 100644 --- a/src/bindings/csharp/openalpr-net/motiondetector-net.cpp +++ b/src/bindings/csharp/openalpr-net/motiondetector-net.cpp @@ -26,7 +26,7 @@ void AlprMotionDetectionNet::ResetMotionDetection(MemoryStream^ memoryStream) void AlprMotionDetectionNet::ResetMotionDetection(array^ byteArray) { std::vector buffer = AlprHelper::ToVector(byteArray); - cv::Mat mat = cv::imdecode(buffer, 1); + cv::Mat mat = cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR); ResetMotionDetection(mat); } @@ -53,7 +53,7 @@ System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(MemoryStream^ me System::Drawing::Rectangle AlprMotionDetectionNet::MotionDetect(array^ byteArray) { std::vector buffer = AlprHelper::ToVector(byteArray); - cv::Mat mat = cv::imdecode(buffer, 1); + cv::Mat mat = cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR); return MotionDetect(mat); } diff --git a/src/bindings/csharp/openalpr-net/openalpr-net.cpp b/src/bindings/csharp/openalpr-net/openalpr-net.cpp index 4ec0d66..fb9183b 100644 --- a/src/bindings/csharp/openalpr-net/openalpr-net.cpp +++ b/src/bindings/csharp/openalpr-net/openalpr-net.cpp @@ -457,7 +457,7 @@ namespace openalprnet { array^ PreWarp(array^ imageBuffer) { std::vector buffer = AlprHelper::ToVector(imageBuffer); - cv::Mat src = cv::imdecode(buffer, 1); + cv::Mat src = cv::imdecode(buffer, CV_LOAD_IMAGE_COLOR); alpr::PreWarp *preWarp = new alpr::PreWarp(m_Impl->getConfig()); cv::Mat warpedImage = preWarp->warpImage(src);