microsoft / opencv

Open Source Computer Vision Library
opencv.org
Apache License 2.0
144 stars 92 forks source link

imread/ imwrite not working properly in Visual Studio 2015 C++ Universal Windows Application #57

Open KKyang opened 9 years ago

KKyang commented 9 years ago

I wrote a code like this and imread only works when the path is in the ms-app folder. I've changed the permission of the application in AppXManifest to make it able to access My Photo but doesn't help either.

The OpenCV branch I'm using is https://github.com/Microsoft/opencv/tree/vs2015-samples

I'm using Visual Studio ver. 14.0.23107.0 D14REL running on Windows 10.10240.

    create_task(openPicker->PickSingleFileAsync()).then([this](StorageFile^ file)
    {

        if (file != nullptr)
        {
            **img = cv::imread(ConvertPath(file->Path));**

            if (!img.empty())
            {
                textBlock->Text = "open Successful!";
                cv::Mat tmp;
                cv::cvtColor(img, tmp, cv::COLOR_BGR2BGRA);
                UpdateImage(tmp);
            }
            else
            {
                textBlock->Text = "open " + file->Path + " failed!";
            }
        }
    });

Update If I load the files in WinRT ways, works.

    create_task(openPicker->PickSingleFileAsync()).then([this](StorageFile^ file)
    {
        if (file != nullptr)
        {
            //WinRT way
            RandomAccessStreamReference^ streamRef = RandomAccessStreamReference::CreateFromFile(file);
            task<IRandomAccessStreamWithContentType^>(streamRef->OpenReadAsync()).
                then([](task<IRandomAccessStreamWithContentType^> thisTask)
            {
                IRandomAccessStreamWithContentType^ fileStream = thisTask.get();
                return BitmapDecoder::CreateAsync(fileStream);
            }).
                then([](task<BitmapDecoder^> thisTask)
            {
                BitmapDecoder^ decoder = thisTask.get();
                return decoder->GetFrameAsync(0);
            }).
                then([this](task<BitmapFrame^> thisTask)
            {
                BitmapFrame^ frame = thisTask.get();

                // Save some information as fields 
                frameWidth = frame->PixelWidth;
                frameHeight = frame->PixelHeight;

                return frame->GetPixelDataAsync();
            }).
                then([this](task<PixelDataProvider^> thisTask)
            {
                PixelDataProvider^ pixelProvider = thisTask.get();
                Platform::Array<byte>^ srcPixels = pixelProvider->DetachPixelData();
                img = cv::Mat(frameHeight, frameWidth, CV_8UC4);
                memcpy(img.data, srcPixels->Data, 4 * frameWidth*frameHeight);

                if (!img.empty())
                {
                    textBlock->Text = "open Successful!";
                    UpdateImage(img);
                }
                else
                {
                    textBlock->Text = "open failed!";
                }
            });

        }
    });

Update 2 The code I use in the sample of imwrite doesn't work either. No file is output. https://github.com/Microsoft/opencv/blob/master/samples/winrt/OcvImageProcessing/OcvImageProcessing/MainPage.xaml.cpp

    StorageFolder^ localFolderRT = ApplicationData::Current->LocalFolder; 
    cv::String localFile = ConvertPath(ApplicationData::Current->LocalFolder->Path) + "\\Lena.png"; 
    return cv::imwrite(localFile, img); 
KKyang commented 9 years ago

@mkostin

mkostin commented 9 years ago

Hi @KKyang, I'm not on this project now, wouldn't be of much help, sorry. My first guess is you're hitting WindowsRT sandbox barriers when using imread/imwrite, this is as much as you can do from within opencv. These restrictions on WinRT are there from the very beginning. BTW OCV is using plain fopen under the hood. With RandomAccessStream you get admittedly bulky but, at the same time, more runtime friendly approach.

KKyang commented 9 years ago

@mkostin Thanks, I'll try to use RandomAccessStream instead now, sadly I cannot find native codec supporting HDR images.

Is it ok to open a new request with the same content at Itseez/opencv?

mkostin commented 9 years ago

@KKyang Sure, please do, you could also reference this ticket to get it tracked. If you manage to come up with a patch, please feel free to submit PR. Thanks for looking into it!