How to convert CLI Image^ into any standard C++ bitmap - c++

I have loaded an JPG image to the Image^ object but now I would like to "go back" to using standard C++ in my program so I would like to somehow convert Image^ object into any BMP class Object(I don't know which c++ class is good).
I would like to edit color of particular pixels in that bitmap.
Please help me do it.
// a.cpp : main project file.
#include "stdafx.h"
#include "Form1.h"
#using <mscorlib.dll> //requires CLI
using namespace System;
using namespace System::IO;
using namespace System::Windows::Media::Imaging;
using namespace System::Windows::Media;
using namespace System::Windows::Controls;
using namespace a;
[STAThreadAttribute]
int main(array<System::String ^> ^args)
{
// Enabling Windows XP visual effects before any controls are created
Application::EnableVisualStyles();
Application::SetCompatibleTextRenderingDefault(false);
// Create the main window and run it
Application::Run(gcnew Form1());
// Open a Stream and decode a JPEG image
Stream^ imageStreamSource = gcnew FileStream("C:/heart.jpg", FileMode::Open, FileAccess::Read, FileShare::Read);
JpegBitmapDecoder^ decoder = gcnew JpegBitmapDecoder(imageStreamSource, BitmapCreateOptions::PreservePixelFormat, BitmapCacheOption::Default);
BitmapSource^ bitmapSource = decoder->Frames[0];//< --mamy bitmape
// Draw the Image
System::Windows::Controls::Image^ myImage = gcnew System::Windows::Controls::Image(); //<--- this image in the Form1 -------
myImage->Source = bitmapSource;
myImage->Stretch = Stretch::None;
//CONVERT MYIMAGE INTO C++ BMP
return 0;
}

try the Image.save method. There you can save to a file or stream and you can specify the file format.

Related

How to configure c++ Zbar scanner to decode only QR-Code data type?

I am using Zbar C++ library to decode QRCode,using this tutorial:
https://www.learnopencv.com/barcode-and-qr-code-scanner-using-zbar-and-opencv/
Here I have to decode only QRCode from an image however using this tutorial it decodes both QRcode and barcodes from an Image.
In tutorial it says to decode only QRCode we have to Configure Zbar Imagescanner properly.
In tutorial they are using following configuration to decode both QRCode and Barcodes
ImageScanner scanner;
scanner.set_config(ZBAR_NONE, ZBAR_CFG_ENABLE, 1);
So to decode only QRCode I am using following configuration:
ImageScanner scanner;
scanner.set_config(ZBAR_QRCODE, ZBAR_CFG_ENABLE, 1);
But using this Zbar configuration still it decodes both QRCode and barcodes data.I am getting Decoded Data type as EAN-13 and QR-Code.
How I can configure Zbar sccanner properly so it decodes only QR-Code Data type?
//Reference:https://www.learnopencv.com/opencv-qr-code-scanner-c-and-python/
#include <iostream>
#include <algorithm>
#include <vector>
#include <zbar.h>
#include <opencv2/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>
using namespace std;
using namespace cv;
using namespace zbar;
typedef struct
{
string type;
string data;
vector <Point> location;
}decodedObject;
// Find and decode barcodes and QR codes
void decode(Mat &im, vector<decodedObject>&decodedObjects)
{
// Create zbar scanner
ImageScanner scanner;
// Configure scanner
scanner.set_config(ZBAR_QRCODE, ZBAR_CFG_ENABLE, 1);
// Convert image to grayscale
Mat imGray;
cvtColor(im, imGray,CV_BGR2GRAY);
// Wrap image data in a zbar image
Image image(im.cols, im.rows, "Y800", (uchar *)imGray.data, im.cols * im.rows);
// Scan the image for barcodes and QRCodes
int n = scanner.scan(image);
// Print results
for(Image::SymbolIterator symbol = image.symbol_begin(); symbol != image.symbol_end(); ++symbol)
{
decodedObject obj;
obj.type = symbol->get_type_name();
obj.data = symbol->get_data();
// Print type and data
cout << "Type : " << obj.type << endl;
cout << "Data : " << obj.data << endl << endl;
decodedObjects.push_back(obj);
}
}
int main(int argc, char *argv[])
{
// Read image
string imagepath = argv[1];
Mat im = imread(imagepath);
// Variable for decoded objects
vector<decodedObject> decodedObjects;
// Find and decode barcodes and QR codes
decode(im, decodedObjects);
return 0;
}
Resulted Output:
Type : QR-Code
Data : http://LearnOpenCV.com
Type : EAN-13
Data : 0036000291452
Expected Output:
Type : QR-Code
Data : http://LearnOpenCV.com
I assume you need to disable all first with
// disable all
scanner.set_config(ZBAR_NONE, ZBAR_CFG_ENABLE, 0);
// enable qr
scanner.set_config(ZBAR_QRCODE, ZBAR_CFG_ENABLE, 1);

"Invalid window handle" error when using FileOpenPicker from C++/WinRT without UWP

I am trying to use C++/WinRT to write something interesting. Having very little experience in Windows programming and no experience in C++/CX, I started out by trying sample program (OCR).
The sample program is about optical character recognition, I modified it to be face detector (console-based). It worked very well.
I want to convert getting file from command-line to file dialog, so I ported the following snippet from C#:
FileOpenPicker picker = FileOpenPicker();
picker.ViewMode(PickerViewMode::Thumbnail);
picker.SuggestedStartLocation(PickerLocationId::PicturesLibrary);
picker.FileTypeFilter().Append(L".jpg");
picker.FileTypeFilter().Append(L".jpeg");
picker.FileTypeFilter().Append(L".png");
StorageFile file = co_await picker.PickSingleFileAsync();
No compile error, but when I run the program, I get this error message:
hresult_error: (0x80070578) Invalid window handle.
I think the error occurs because it is a console-based program (wmain), not wWinMain.
I tried to find a solution online, but they are all about UWP. Please provide a solution that does not involve UWP and must be able to compile from cl.exe directly.
Note:
According to UWP APIs callable from a classic desktop app, if an API has DualApiPartitionAttribute attribute, it will work in classic desktop app, otherwise it won't. For example, Geolocator has this attribute so it will work.
However, even though FaceDetector does not have this attribute it still works proven in my toy program.
Anything from Windows::UI definitely requires UWP (although there is https://aka.ms/windowsui/inwin32). FileOpenPicker does not have this attribute but it is not under Windows::UI, so there might be a chance it can be workaround.
Complete code:
#pragma comment(lib, "windowsapp")
#include <winrt/Windows.Storage.Pickers.h>
#include <winrt/Windows.Storage.Streams.h>
#include <winrt/Windows.Graphics.Imaging.h>
#include <winrt/Windows.Media.FaceAnalysis.h>
using namespace winrt;
using namespace std::chrono;
using namespace Windows::Foundation;
using namespace Windows::Storage;
using namespace Windows::Storage::Pickers;
using namespace Windows::Storage::Streams;
using namespace Windows::Graphics::Imaging;
using namespace Windows::Media::FaceAnalysis;
using Windows::Foundation::Collections::IVector;
IAsyncOperation<int> AsyncSample() {
FileOpenPicker picker = FileOpenPicker();
picker.ViewMode(PickerViewMode::Thumbnail);
picker.SuggestedStartLocation(PickerLocationId::PicturesLibrary);
picker.FileTypeFilter().Append(L".jpg");
picker.FileTypeFilter().Append(L".jpeg");
picker.FileTypeFilter().Append(L".png");
StorageFile file = co_await picker.PickSingleFileAsync();
//StorageFile file = co_await StorageFile::GetFileFromPathAsync(
// L"C:\\Users\\user\\Pictures\\20170318_202325.jpg");
IRandomAccessStream stream = co_await file.OpenAsync(FileAccessMode::Read);
BitmapDecoder decoder = co_await BitmapDecoder::CreateAsync(stream);
SoftwareBitmap bitmap = co_await decoder.GetSoftwareBitmapAsync();
FaceDetector detector = co_await FaceDetector::CreateAsync();
SoftwareBitmap converted =
SoftwareBitmap::Convert(bitmap, BitmapPixelFormat::Nv12);
IVector<DetectedFace> result = co_await detector.DetectFacesAsync(converted);
printf("Detection done\n");
for (auto& face : result) {
BitmapBounds box = face.FaceBox();
printf("[%u %u %u %u]\n", box.X, box.Y, box.Width, box.Height);
}
printf("Printing done\n");
return 0;
}
int wmain() {
init_apartment();
try {
int res = AsyncSample().get();
printf("%d\n", res);
} catch (hresult_error& e) {
printf("hresult_error: (0x%8X) %ls\n", e.code(), e.message().c_str());
}
return 0;
}
So this was the modification neeeded:
IAsyncOperation<int> AsyncSample() {
HWND hwnd = GetConsoleWindow(); // #include <windows.h>
FileOpenPicker picker = FileOpenPicker();
picker.as<IInitializeWithWindow>()->Initialize(hwnd);

VideoCapture not working C++ windows

So I have played around in OpenCV a bunch before and never run into this problem. I am implementing a MeanShift algorithm and trying to do it on video devices, images, and videos. Devices and images work; however, no matter what I try, when I run VideoCapture on my filename (whether setting it in the Constructor or using the VideoCapture::open() method, and whether local or with a full path) I always get stuck in my error check.
Thoughts? Ideas? code below. running in Visual Studio 2012
#include "opencv2\highgui\highgui.hpp"
#include "opencv2\core\core.hpp"
#include "opencv2\opencv.hpp"
#include "opencv2\video\video.hpp"
#include <string>
using cv::Mat;
using std::string;
enum Filetype{Image, Video};
int main(int argc, char* argv[])
{
string filename = "short_front.avi";// "C:\\Users\\Jonathan\\Videos\\short_front.mp4"; //"hallways.jpg";
Mat cv_image; //convert to unsigned char * with data
Mat filtImage_;
Mat segmImage_;
Mat whiteImage_;
cv::VideoCapture vid;
vid.open("C:/Users/Jonathan/Desktop/TestMeanShift/TestMeanShift/short_front.avi");
cv::waitKey(1000);
if ( !vid.isOpened() ){
throw "Error when reading vid";
cv::waitKey(0);
return -1;
}
// cv_image = cv::imread(filename);//, CV_LOAD_IMAGE_COLOR);
// if(! cv_image.data){
// std::cerr << "Image Failure: " << std::endl;
// system("pause");
// return -1;
// }
//Mat cv_image_gray;
//cv::cvtColor(cv_image,cv_image_gray,CV_RGB2GRAY);
for (;;)
{
vid >> cv_image;
if ( !cv_image.data)
continue;
cv::imshow("Input",cv_image); //add a normal window here to resizable
}
EDIT: This is a distinct problem from the one listed here because it deals with a specific corner case: VideoCapture and ImageCapture both work, only not VideoCapture with a file. When it doesn't work, the code runs properly, except that the "video" it creates is incomplete as it didn't open properly. Therefore, as the code above does not crash in compile time or run time, the only indicator is bad output (6KB video output file). If you are having issues not with the corner case I am describing but general issues with the above functions in OpenCV, the aforementioned link could help you.

ERROR: identifier "img" is undefined

I'm beginner to openCV. I dowloaded opencv2.4.5 and visual studio express 2012 then i followed this link http://opencv-srf.blogspot.in/2013/05/installing-configuring-opencv-with-vs.html for setup everything in environment variable etc. Then i followed below link http://opencv-srf.blogspot.in/2013/06/load-display-image.html to create sample application. I included proper #include path. But i'm getting error.
#include "stdafx.h"
#include <C:\opencv\build\include\opencv\cv.h>
#include <C:\opencv\build\include\opencv\cxcore.h>
#include <C:\opencv\build\include\opencv\highgui.h>
#include "C:\opencv\build\include\opencv2\highgui\highgui.hpp"
#include <iostream>
using namespace cv;
using namespace std;
int main( int argc, const char** argv )
{
Mat img = imread("MyPic.JPG", CV_LOAD_IMAGE_UNCHANGED); //read the image data in the file "MyPic.JPG" and store it in 'img'
if (img.empty()) //check whether the image is loaded or not
{
cout << "Error : Image cannot be loaded..!!" << endl;
//system("pause"); //wait for a key press
return -1;
}
namedWindow("MyWindow", CV_WINDOW_AUTOSIZE); //create a window with the name "MyWindow"
imshow("MyWindow", img); //display the image which is stored in the 'img' in the "MyWindow" window
waitKey(0); //wait infinite time for a keypress
destroyWindow("MyWindow"); //destroy the window with the name, "MyWindow"
return 0;
}
please do not use an absolute path for the includes, this is totally non-portable.
it should look like this:
// the usual suspects:
#include "opencv2\core\core.hpp" // Mat is defined here.
#include "opencv2\imgproc\imgproc.hpp"
#include "opencv2\highgui\highgui.hpp"
also, to make this work, your "additional include folders" should point to "opencv/build/include"
and avoid the old c-api headers, like cv.h, highgui.h, cxcore.h

How to decode an animated gif File in MFC2010

Deal all,
I need to decode an animated gif format picture into some bitmap files in MFC2010. Is there any library to decode a gif picture? I cannot use GDIPlus because the program has to run on windows XP. I do appreciate if someone provides me with a library, Activex, dll or anything similar.
Many Thanks,
Shervin Zargham
It's pretty simple using ImageMagick's C++ API (Magick++) :
/* list of Image to store the GIF's frames */
std::vector<Magick::Image> imageList;
/* read all the frames of the animated GIF */
Magick::readImages( &imageList, "animated.gif" );
/* optionnally coalesce the frame sequence depending on the expected result */
Magick::coalesceImages( &imageList, imageList.begin(), imageList.end());
/* store each frame in a separate BMP file */
for(unsigned int i = 0; i < imageList.size(); ++i) {
std::stringstream ss;
ss << "frame" << i << ".bmp";
imageList[i].write(ss.str());
}
WIC (included in Vista, available for XP) offers CLSID_WICGifDecoder, a COM component.
Try this using ImageMagick's C++ API (Magick++) ,tested on VS210:
#include <Magick++.h>
#include <string>
#include <iostream>
#include <list>
using namespace std;
using namespace Magick;
void kk(char * nombre, char *ext)
{
/* list of Image to store the GIF's frames */
std::list<Magick::Image> imageList;
/* read all the frames of the animated GIF */
Magick::readImages( &imageList, nombre );
/* compone las diferencias para obtener los cuadros reales */
Magick::coalesceImages(&imageList,imageList.begin( ),imageList.end( ));
/* store each frame in a separate BMP file */
list <Magick::Image>::iterator it;
int i=1;
for ( it = imageList.begin( ); it != imageList.end( ); it++ , i++)
{
std::string name = "frame" + to_string((_Longlong)(i)) + ext ;
it->write(name);
}
}
int main( int /*argc*/, char ** argv)
{
// Initialize ImageMagick install location for Windows
InitializeMagick(*argv);
try {
kk("luni0.gif", ".png"); // using ".bmp", ".jpg", ".png", OK
return 0;
}
catch( exception &error_ )
{
cout << "Caught exception: " << error_.what() << endl;
return 1;
}
}
It's been a long time, but I recall once using OleLoadPicture to open GIF and PNG files on old versions of Windows, though the documentation seems to suggest that it's only for BMP, ICO, and WMF.