微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

将位图添加到 Windows 运行时剪贴板

如何解决将位图添加到 Windows 运行时剪贴板

我正在开发一个 C++ 应用程序,我需要能够将位图添加到 Windows 运行时剪贴板。我的选择是使用 WRL 或 WinRT,所以我选择了 WRL,因为它似乎有(稍微)更多的文档。经过一番摆弄后,我有一些代码可以将文本添加到剪贴板:

    RoInitializeWrapper initialise(RO_INIT_SINGLETHREADED);
    if (Failed(initialise))
    {
        return 1;
    }

    ComPtr<IClipboardStatics> clipboard;
    HRESULT hr2 = GetActivationFactory(HStringReference(RuntimeClass_Windows_ApplicationModel_DataTransfer_Clipboard).Get(),&clipboard);

    ComPtr<IDataPackage> dataPackage;
    hr2 = ActivateInstance(HStringReference(RuntimeClass_Windows_ApplicationModel_DataTransfer_DataPackage).Get(),&dataPackage);

    hr2 = dataPackage.Get()->SetText(HStringReference(L"Testing 1 2 3 4").Get());

    hr2 = clipboard.Get()->SetContent(dataPackage.Get());

然而,事实证明添加位图要困难得多。我花了很多时间查看源代码、阅读文档和编写测试代码,最终得到以下结果(注意我从 HD 读取了一个 BMP 文件用于测试目的):

    HRESULT hr2;

    ComPtr<IDataWriter> imageDataWriter;
    ComPtr<IRandomAccessstream> imagestream;
    ComPtr<IRandomAccessstreamReference> imagestreamReference;
 
    RoInitializeWrapper initialise(RO_INIT_SINGLETHREADED);
    if (Failed(initialise))
    {
         return 1;
    }

    hr2 = ActivateInstance(HStringReference(RuntimeClass_Windows_Storage_Streams_InMemoryRandomAccessstream).Get(),imagestream.GetAddressOf());


    ComPtr<IoUtputStream> outputStream;
    hr2 = imagestream.As(&outputStream);

    ComPtr<IDataWriterFactory> dataWriterFactory;
    hr2 = GetActivationFactory(HStringReference(RuntimeClass_Windows_Storage_Streams_DataWriter).Get(),dataWriterFactory.GetAddressOf());

    hr2 = dataWriterFactory->CreateDataWriter(outputStream.Get(),imageDataWriter.GetAddressOf());

    BYTE* data = nullptr;

    std::streampos size;
    std::ifstream in(L"c:\\temp\\background.bmp",std::ios::in|std::ios::binary|std::ios::ate);
    if (in.is_open())
    {
        size = in.tellg();

        data = new BYTE[size];
        in.seekg(0,std::ios::beg);
        in.read((char*) data,size);
        in.close();
    }

    hr2 = imageDataWriter->WriteBytes(size,data);

    ComPtr<IDataPackage> dataPackage;
    hr2 = ActivateInstance(HStringReference(RuntimeClass_Windows_ApplicationModel_DataTransfer_DataPackage).Get(),&dataPackage);

    ComPtr<IRandomAccessstreamReferenceStatics> streamRefFactory;
    hr2 = GetActivationFactory(HStringReference(RuntimeClass_Windows_Storage_Streams_RandomAccessstreamReference).Get(),streamRefFactory.GetAddressOf());

    hr2 = streamRefFactory->CreateFromStream(imagestream.Get(),imagestreamReference.GetAddressOf());

    hr2 = dataPackage.Get()->SetBitmap(imagestreamReference.Get());

    hr2 = dataPackage->put_RequestedOperation(DataPackageOperation::DataPackageOperation_copy);

    ComPtr<IClipboardStatics> clipboard;
    hr2 = GetActivationFactory(HStringReference(RuntimeClass_Windows_ApplicationModel_DataTransfer_Clipboard).Get(),&clipboard);

    hr2 = clipboard.Get()->SetContent(dataPackage.Get());

    clipboard->Flush();

所有 WRL 函数都返回 S_OK,但实际上剪贴板中没有任何内容。当 IRandomAccessstreamReference 超出范围时,我确实收到了异常,因此这可能是一个线索。

任何关于我做错了什么的线索?这是我第一次使用 Windows 运行时,老实说,我发现使用它非常令人沮丧。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。