XamarinMediaManager
XamarinMediaManager copied to clipboard
How to manage errors related to the URL or to connectivity?
Hello,
I use the XamarinMediaManager in a Xamarin.Forms project, to play audio from a web radio.
But I would like to manage error cases, like when the URL is no longer available, or if there is not internet access for example.
I launch the audio stream like this:
var mediaItem = await CrossMediaManager.Current.Play(audioUrl);
If I use a "wrong" URL, nothing happens, but I didn't found how to "identify" this case. It's the same thing if I activate the airplane mode.
I would like to display an error message to the user in both cases, so he could understand why the audio doesn't launch.
Is there a way to manage this?
From the top of my head: there's a OnMetadataUpdated that you can subscribe to for updates. mediaItem.MetadataUpdated += (sender, args) => { var title = args.MediaItem.Title; // Perhands check for null values and act accordingly. };
Thanks @RichardSV15, it's seems the better solution.
Finally, I've did like this:
var mediaItem = await mediaManager.Play(radioUrl);
CurrentTitle = mediaItem.Title;
Debug.WriteLine($"PlayStopAsync() - CurrentTitle: {CurrentTitle.ToString()}");
mediaItem.MetadataUpdated += (sender, args) =>
{
CurrentTitle = args.MediaItem.Title;
Debug.WriteLine($"PlayStopAsync() - mediaItem.MetadataUpdated - CurrentTitle: {CurrentTitle}");
};
I check the Title
directly from the mediaItem
: it seems the MetadataUpdated
is never fired, from a valid or from a invalid URL...
However, I find strange that if I use an invalid URL, the State
varies to Paused
:
private void OnStateChanged(object sender, MediaManager.Playback.StateChangedEventArgs e)
{
Debug.WriteLine($"OnStateChanged() - StateChangedEventArgs e: {e.State.ToString()}");
...
}
Cause if the user try to press the "Play" button a second time, the State
varies to Buffering
and the to Playing
. To abord this, I'm forced to call mediaManager.Stop()
if the CurrentTitle
is null.
So it works now, but it's not very clear...
Finally, I've implemented a solution that one have suggested by using MediaItem.Title
:
var mediaItem = await CrossMediaManager.Current.Play(radioUrl);
var currentTitle = mediaItem.Title;
This only works for iOS, on Android the use of mediaItem.Title
raise an Exception...
So, to manage Android case, I use the MediaItemFailed
:
CrossMediaManager.Current.MediaItemFailed += OnCurrentMediaItemFailed;
The event is only raised after 1 minute on Android, and it's not raised at all on iOS.
This solution is not perfect and is no the same for 2 platforms, but I don't found a better one yet...
Thanks for bringing it up and posting your solution. I'll be implementing it myself, on dead links that users may be trying replay... The events not firing seems to be consistent across a few other issues that I've seen come up with the library. Not ideal but still this library is still the best go to for media management
In add to this, I would like to know if there is a way to "cancel" a Play()
request?
I've tried to call Stop()
in case of errros, but it doesn't seem having any effet: the State is still Pause
or Buffering
after this...
I've did some investigations, and it seems that the behaviour is not the same on iOS and Android.
As a reminder, I would like to manage errors that can occur when the user try to play a webradio stream.
On Android, I use the MediaItemFailed
event, that is raised after 1 minute:
CrossMediaManager.Current.MediaItemFailed += OnCurrentMediaItemFailed;
On iOS the event is not raised, so I check the MediaItem.Title
like this:
var mediaItem = await CrossMediaManager.Current.Play(radioUrl);
var currentTitle = mediaItem.Title;
But in both cases, I would to display an error message to the user, and to reset CrossMediaManager.Current.State
to Stopped
.
For this, I call the Stop()
method when an issue is detected:
await CrossMediaManager.Current.Stop();
But this seems only working on Android. On iOS, the State
is still Pause
or Buffering
after this...
Is there any explanation?