How to get videos with PHVideo from iCloud?

Pelin Konaray 291 Reputation points
2020-12-16T14:18:09.837+00:00

Hi,

I implemented multimedia picker (for images and videos) with DependencyService on Xamarin.Forms app. I have a problem on iCloud videos.
When I select video that is on icloud, I can't get it.

My implementation is:

async void FinishedPickingAssets(object sender, MultiAssetEventArgs args)  
        {  
            IList<MediaFile> results = new List<MediaFile>();  
            TaskCompletionSource<IList<MediaFile>> tcs = new TaskCompletionSource<IList<MediaFile>>();  
  
            try   
            {   
                var options = new PHImageRequestOptions()  
                {  
                    NetworkAccessAllowed = true  
                };  
  
                options.Synchronous = false;  
                options.ResizeMode = PHImageRequestOptionsResizeMode.Fast;  
                options.DeliveryMode = PHImageRequestOptionsDeliveryMode.HighQualityFormat;  
                bool completed = false;  
                for (var i = 0; i < args.Assets.Length; i++)  
                {  
                    var asset = args.Assets[i];  
  
                    string fileName = string.Empty;  
                    if (UIDevice.CurrentDevice.CheckSystemVersion(9, 0))  
                    {  
                        fileName = PHAssetResource.GetAssetResources(asset).FirstOrDefault().OriginalFilename;  
                        fileName = Path.GetFileNameWithoutExtension(fileName) + "(" + i.ToString() + ")" + Path.GetExtension(fileName);  
                    }  
  
                    switch (asset.MediaType)  
                    {  
                        case PHAssetMediaType.Video:  
                        {  
                                var vOptions = new PHVideoRequestOptions();  
                                vOptions.NetworkAccessAllowed = true;  
                                vOptions.Version = PHVideoRequestOptionsVersion.Original;  
                                vOptions.DeliveryMode = PHVideoRequestOptionsDeliveryMode.Automatic;  
                                string videoUrl = "";  
  
                                PHImageManager.DefaultManager.RequestAvAsset(asset, vOptions, (avAsset, audioMix, vInfo) =>   
                                {  
                                    DispatchQueue.MainQueue.DispatchAsync(() => {  
  
                                        var error = vInfo.ObjectForKey(PHImageKeys.Error);  
                                          
                                        if (avAsset != null)  
                                        {  
                                            videoUrl = ((AVFoundation.AVUrlAsset)avAsset).Url.Path;  
                                        }  
                                        var meFile = new MediaFile()  
                                        {  
                                            FileName = fileName,  
                                            FilePath = videoUrl  
                                        };  
  
                                        using (Stream source = File.OpenRead(videoUrl))  
                                        {  
                                            meFile.FileSize = source.Length;  
                                        }  
                                        results.Add(meFile);  
                                        OnMediaPicked?.Invoke(this, meFile);  
  
                                        if (args.Assets.Length == results.Count && !completed)  
                                        {  
                                            completed = true;  
                                            tcs.TrySetResult(results);  
                                        }  
                                    });  
                                });  
                        }  
                        break;  
                    default:  
                        PHImageManager.DefaultManager.RequestImageData(asset, options, (data, dataUti, orientation, info) =>  
                        {  
  
                            string path = FileHelper.GetOutputPath(MediaFileType.Image, TemporalDirectoryName, fileName);  
  
                            if (!File.Exists(path))  
                            {  
                                Debug.WriteLine(dataUti);  
                                var imageData = data;  
                                imageData?.Save(path, true);  
                            }  
  
                            var meFile = new MediaFile()  
                            {  
                                FileName = fileName,  
                                FilePath = path,  
                                FileSize = File.ReadAllBytes(path).Length  
                            };  
  
                            results.Add(meFile);  
                            OnMediaPicked?.Invoke(this, meFile);  
                            if (args.Assets.Length == results.Count && !completed)  
                            {  
                                completed = true;  
                                tcs.TrySetResult(results);  
                            }  
  
                        });  
                        break;  
                    }  
                }  
            }  
            catch  
            {  
                tcs.TrySetResult(results);  
  
                string automationId = "UnexpectedSituationMessage";  
                GeneralOperations.OpenToastMessage("Unexpected Situation", automationId);  
            }  
  
            mediaPickTcs?.TrySetResult(await tcs.Task);  
        }  

When I try to select iCloud object, I get following error:

48811-vid-lib-error.jpg

How can I take videos with multiple select from icloud?

Thank you in advance.

Xamarin
Xamarin
A Microsoft open-source app platform for building Android and iOS apps with .NET and C#.
5,289 questions
{count} votes

1 answer

Sort by: Most helpful
  1. Pelin Konaray 291 Reputation points
    2020-12-18T06:44:48.973+00:00

    Hi,

    I did a sample for my issue. Git repo:
    https://github.com/Pelinalpp/XamarinMultiMedia

    But I want to say one last thing. I have no problem with a video on the phone. I have problem with video on only iCloud. It also appear on video picker. But when i select it, it comes null on this line: "if (avAsset != null)". So that I can't get file. When I pull it to phone from iCloud. I can get it with picker

    PHImageManager.DefaultManager.RequestAvAsset(asset, vOptions, (avAsset, audioMix, vInfo) =>
                                    {
                                        DispatchQueue.MainQueue.DispatchAsync(() => {
    
                                            var error = vInfo.ObjectForKey(PHImageKeys.Error);
    
                                            if (avAsset != null)
                                            {
                                                videoUrl = ((AVFoundation.AVUrlAsset)avAsset).Url.Path;
                                            }
    
                                            var meFile = new MediaFile()
                                            {
                                                FileName = fileName,
                                                FilePath = videoUrl
                                            };
    
                                            using (Stream source = File.OpenRead(videoUrl))
                                            {
                                                meFile.FileSize = source.Length;
                                            }
                                            results.Add(meFile);
                                            OnMediaPicked?.Invoke(this, meFile);
    
                                            if (args.Assets.Length == results.Count && !completed)
                                            {
                                                completed = true;
                                                tcs.TrySetResult(results);
                                            }
    
                                        });
    

    And I also checked iCloud photos is turn on.