locked
Translate the BitmapEncoder code example in C++ please

    Question

  • In my app, I need to save the on-screen rendering content to an image file and plan to use BitmapEncode class after some Bing searches.

    This article titled "How to encode a new image (Windows Store apps using C#/VB/C++ and XAML)" provides a good example but unfortunately the code is C#, which cannot be used in my C++ app. I could not translate the code to C++ as there are two asyncronous tasks (file.OpenAsync and BitmapEncoder.CreateAsync) in the code. Could someone kindly to rewrite the code in C++? Thanks! Oh, another plea to Microsoft, could you give C++ code in your MSDN articles? we are tired of reading C#.


    • Edited by Leonard Wednesday, July 31, 2013 3:25 PM
    Wednesday, July 31, 2013 3:24 PM

Answers

  • Here you go:

    I added the following namespaces to a blank app page template.

    using namespace Windows::Storage;
    using namespace Windows::Storage::Pickers;
    using namespace Windows::Storage::Provider;
    using namespace Windows::Storage::Streams;
    using namespace concurrency;

    Added #include <ppltasks.h> to make the async work

    void SimpleImageEncode::MainPage::EncodeImage()
    {
    	FileSavePicker^ savePicker = ref new FileSavePicker(); 
    	auto plainTextExtensions = ref new Platform::Collections::Vector<String^>(); 
    	plainTextExtensions->Append(".jpg"); 
    	savePicker->FileTypeChoices->Insert("JPEG Image", plainTextExtensions); 
    	savePicker->SuggestedFileName = "MyImage"; 
    	savePicker->SuggestedStartLocation = PickerLocationId::Desktop; 
    
    	create_task(savePicker->PickSaveFileAsync()).then([this](StorageFile^ file) 
    	{ 
    		if(file)
    		{
    			create_task(file->OpenAsync(Windows::Storage::FileAccessMode::ReadWrite)).then([this](IRandomAccessStream^ stream)
    			{
    				auto encoderId = Windows::Graphics::Imaging::BitmapEncoder::JpegEncoderId;
    				stream->Size = 0;
    
    				create_task(Windows::Graphics::Imaging::BitmapEncoder::CreateAsync(
    					encoderId,
    					stream
    					)).then([this](Windows::Graphics::Imaging::BitmapEncoder^ encoder)
    				{
    					// An array representing 2x2 red, opaque pixel data
    					Array<byte>^ pixels = {			
    						255, 0, 0, 255,
    						255, 0, 0, 255,
    						255, 0, 0, 255,
    						255, 0, 0, 255
    					};
    
    					encoder->SetPixelData(
    						Windows::Graphics::Imaging::BitmapPixelFormat::Rgba8,
    						Windows::Graphics::Imaging::BitmapAlphaMode::Straight,
    						2, // pixel width
    						2, // pixel height
    						96, // horizontal DPI
    						96, // vertical DPI
    						pixels
    						);
    					encoder->FlushAsync();
    				});
    			});
    		}
    	});
    }
    

    • Proposed as answer by jrboddie Wednesday, July 31, 2013 5:57 PM
    • Marked as answer by Leonard Wednesday, July 31, 2013 10:12 PM
    Wednesday, July 31, 2013 5:55 PM

All replies

  • Here you go:

    I added the following namespaces to a blank app page template.

    using namespace Windows::Storage;
    using namespace Windows::Storage::Pickers;
    using namespace Windows::Storage::Provider;
    using namespace Windows::Storage::Streams;
    using namespace concurrency;

    Added #include <ppltasks.h> to make the async work

    void SimpleImageEncode::MainPage::EncodeImage()
    {
    	FileSavePicker^ savePicker = ref new FileSavePicker(); 
    	auto plainTextExtensions = ref new Platform::Collections::Vector<String^>(); 
    	plainTextExtensions->Append(".jpg"); 
    	savePicker->FileTypeChoices->Insert("JPEG Image", plainTextExtensions); 
    	savePicker->SuggestedFileName = "MyImage"; 
    	savePicker->SuggestedStartLocation = PickerLocationId::Desktop; 
    
    	create_task(savePicker->PickSaveFileAsync()).then([this](StorageFile^ file) 
    	{ 
    		if(file)
    		{
    			create_task(file->OpenAsync(Windows::Storage::FileAccessMode::ReadWrite)).then([this](IRandomAccessStream^ stream)
    			{
    				auto encoderId = Windows::Graphics::Imaging::BitmapEncoder::JpegEncoderId;
    				stream->Size = 0;
    
    				create_task(Windows::Graphics::Imaging::BitmapEncoder::CreateAsync(
    					encoderId,
    					stream
    					)).then([this](Windows::Graphics::Imaging::BitmapEncoder^ encoder)
    				{
    					// An array representing 2x2 red, opaque pixel data
    					Array<byte>^ pixels = {			
    						255, 0, 0, 255,
    						255, 0, 0, 255,
    						255, 0, 0, 255,
    						255, 0, 0, 255
    					};
    
    					encoder->SetPixelData(
    						Windows::Graphics::Imaging::BitmapPixelFormat::Rgba8,
    						Windows::Graphics::Imaging::BitmapAlphaMode::Straight,
    						2, // pixel width
    						2, // pixel height
    						96, // horizontal DPI
    						96, // vertical DPI
    						pixels
    						);
    					encoder->FlushAsync();
    				});
    			});
    		}
    	});
    }
    

    • Proposed as answer by jrboddie Wednesday, July 31, 2013 5:57 PM
    • Marked as answer by Leonard Wednesday, July 31, 2013 10:12 PM
    Wednesday, July 31, 2013 5:55 PM
  • Thank you very much jrboddie.
    Wednesday, July 31, 2013 10:12 PM