Winapi 是否可以将UWP存储文件拖放到使用CreateStreamedFileFromUriAsyc创建的桌面上

Winapi 是否可以将UWP存储文件拖放到使用CreateStreamedFileFromUriAsyc创建的桌面上,winapi,drag-and-drop,uwp,storagefile,Winapi,Drag And Drop,Uwp,Storagefile,目标: 我要做的是将一个GridViewItem从应用程序外部的UWP应用程序中的GridView拖动到桌面资源管理器。在drop事件期间,我想从internet下载一个文件并创建一个存储文件,用于填充数据包。我希望将此StorageFile复制到桌面。不幸的是,当UWP拖放使用延迟时(使用SetDataProvider),当您离开应用程序窗口时,请求被激活,您必须用要传输的对象填充数据包。因此,在我看来,我需要使用一种延迟类型的StorageFile,它是使用createstreamdfile

目标: 我要做的是将一个
GridViewItem
从应用程序外部的UWP应用程序中的
GridView
拖动到桌面资源管理器。在drop事件期间,我想从internet下载一个文件并创建一个
存储文件
,用于填充
数据包
。我希望将此
StorageFile
复制到桌面。不幸的是,当UWP拖放使用延迟时(使用
SetDataProvider
),当您离开应用程序窗口时,请求被激活,您必须用要传输的对象填充
数据包。因此,在我看来,我需要使用一种延迟类型的
StorageFile
,它是使用
createstreamdfilefromuriasyc
创建的

我不希望每次开始执行拖放操作时都预下载数据。我只想下载数据,当我真的把它放在合法的地方复制

  • 我知道如何使用延迟请求将预先存在的
    StorageFile
    从UWP拖放到Explorer(桌面)
  • 我还知道如何使用
    CreateStreamedFileFromUriAsyc
    创建
    StorageFile
    ,它将为您提供一个
    StorageFile
    ,仅在请求数据时才下载数据 当我尝试将这两种想法结合起来时,windows资源管理器会给我一个错误“界面不受支持”

    如果我使用完全相同的代码,但只是在延迟拖动处理程序期间通过调用GetBasicPropertiesAsync之类的函数来获取文件内容,那么只有在下载文件之前将拖动保持在桌面上,它才会起作用。当拖动图标从“禁止”图标更改为“复制”时,我可以看到它完成了。如果在完成之前松开鼠标按钮,则不会发生复制,也不会出现错误

    显然,我希望不必在延迟处理程序上手动启动拖放即可下载。有什么想法吗?这可能吗

    (是的,我知道创建正确文件扩展名的代码是错误的/不完整的,但这与此无关……)

    //构造函数中的DragStarted处理程序
    DragItemsStartedCommand=ReactiveCommand.Create((e)=>
    {
    _dragItems=e.Items.Cast();
    e、 Data.Properties.Title=“传输文件”;
    e、 Data.Properties.Description=“传输文件的描述”;
    e、 Data.Properties.FileTypes.Add(StandardDataFormats.StorageItems);
    e、 Data.SetDataProvider(Windows.ApplicationModel.DataTransfer.StandardDataFormats.StorageItems,OnFerredStorageFileRequestedHandler);
    e、 Data.RequestedOperation=DataPackageOperation.Copy;
    });
    //延迟请求处理程序
    异步无效OnFerredStorageFileRequestedHandler(DataProviderRequest请求)
    {
    DataProviderDeleral Deleral=请求.getDeleral();
    尝试
    {
    Task=null;
    等待Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.Normal,async()=>
    {
    任务=下载存储文件();
    });
    var结果=等待任务;
    请求设置数据(结果);
    }
    捕获(例外情况除外)
    {
    //处理异常
    }
    最后
    {
    延迟。完成();
    Debug.WriteLine(“延迟完成!!!”;
    }
    }
    //使用延迟加载任务创建StorageFile
    异步任务下载存储文件()
    {
    List storageItems=新列表();
    foreach(dragItems中的var项目)
    {
    var request=new RestSharp.RestRequest();
    var defaultItemType=ItemType.MSWord;
    开关(项目.mimetypetransed)
    {
    case ItemType.GoogleDocument:
    case ItemType.google电子表格:
    案例ItemType.GooglePresentation:
    case ItemType.GoogleDrawing:
    case ItemType.GoogleScript:
    request.Resource=$“files/{item.File.id}/export”;
    request.AddParameter(“mimeType”,Statics.ItemTypeDictionary.First(x=>x.Value==defaultItemType).Key);
    打破
    违约:
    request.Resource=$“files/{item.File.id}”;
    AddParameter(“alt”、“media”);
    打破
    }
    字符串fileName=“”;
    if(item.File.name.EndsWith($“{Statics.ItemExtensionDictionary[defaultItemType]}”))
    fileName=$“{item.File.name}”;
    其他的
    fileName=$“{item.File.name}.{Statics.ItemExtensionDictionary[defaultItemType]}”;
    var uri=account.Client.GetAuthorizedUriForDownload(请求);
    var thumbnail=RandomAccessStreamReference.CreateFromFile(等待StorageFile.GetFileFromApplicationUriAsync(新Uri(“ms”)-appx:///StoreLogo.png")));
    var storageFileDeferred=wait-StorageFile.CreateStreamedFileFromUriAsync(文件名、uri、缩略图);
    //var props=await-storageFileDeferred.GetBasicPropertiesAsync();
    storageItems.Add(文件);
    }
    归还物品;
    }
    
    GitHub重新报告此问题:

  • 由于StorageFile(+基础数据)已经在assets文件夹中,所以第一页是一个常规的拖到桌面的工作方式
  • 第二页显示使用使用CreateStreamedFileFromUriAsync创建的存储文件时生成的错误
  • 第三个页面使用了相同类型的StorageFile,但有一种黑客手段,可以强制同步检索数据。桌面冻结一秒钟,直到数据准备就绪

  • 从最近的Windows更新开始,UWP应用程序上存储文件的拖放由系统自动处理


    从最近的Windows更新UWP应用程序i上的拖放存储文件
    //DragStarted Handler in constructor
    DragItemsStartedCommand = ReactiveCommand.Create<DragItemsStartingEventArgs>((e) =>
            {
                _dragItems = e.Items.Cast<ItemViewModel>();
                e.Data.Properties.Title = "Transfer file";
                e.Data.Properties.Description = "desscription of transfering a file";
                e.Data.Properties.FileTypes.Add(StandardDataFormats.StorageItems);
                e.Data.SetDataProvider(Windows.ApplicationModel.DataTransfer.StandardDataFormats.StorageItems, OnDeferredStorageFileRequestedHandler);
                e.Data.RequestedOperation = DataPackageOperation.Copy;
            });
    
    
     //Deferred request handler
        async void OnDeferredStorageFileRequestedHandler(DataProviderRequest request)
        {
            DataProviderDeferral deferral = request.GetDeferral();
            try
            {
                Task<IEnumerable<StorageFile>> task = null;
                await Windows.ApplicationModel.Core.CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, async () =>
                {
                    task = DownloadStorageFiles();
                });
                var result = await task;
                request.SetData(result);
            }
    
            catch (Exception ex)
            {
                // Handle the exception
            }
    
            finally
            {
                deferral.Complete();
                Debug.WriteLine("deferral complete!!!");
            }
    
        }
    
    //Create StorageFile with deferred loading Task
        async Task<IEnumerable<StorageFile>> DownloadStorageFiles()
        {
            List<StorageFile> storageItems = new List<StorageFile>();
            foreach (var item in _dragItems)
            {
                var request = new RestSharp.RestRequest();
            var defaultItemType = ItemType.MSWord;
            switch (item.MimeTypeTranslated)
            {
                case ItemType.GoogleDocument:
                case ItemType.GoogleSpreadsheet:
                case ItemType.GooglePresentation:
                case ItemType.GoogleDrawing:
                case ItemType.GoogleScript:
                    request.Resource = $"files/{item.File.id}/export";
                    request.AddParameter("mimeType", Statics.ItemTypeDictionary.First(x => x.Value == defaultItemType).Key);
                    break;
                default:
                    request.Resource = $"files/{item.File.id}";
                    request.AddParameter("alt", "media");
                    break;
            }
            string fileName = "";
            if (item.File.name.EndsWith($".{Statics.ItemExtensionDictionary[defaultItemType]}"))
                fileName = $"{item.File.name}";
            else
                fileName = $"{item.File.name}.{Statics.ItemExtensionDictionary[defaultItemType]}";
            var uri = account.Client.GetAuthorizedUriForDownload(request);
    
            var thumbnail = RandomAccessStreamReference.CreateFromFile(await StorageFile.GetFileFromApplicationUriAsync(new Uri("ms-appx:///StoreLogo.png")));
            var storageFileDeferred = await StorageFile.CreateStreamedFileFromUriAsync(fileName, uri , thumbnail);
            //var props = await storageFileDeferred.GetBasicPropertiesAsync();                
             storageItems.Add(file);
            }
            return storageItems;
        }