On Thu, Oct 23, 2014 at 10:08 AM, Andrea Marchesini
<
amarc...@mozilla.com> wrote:
> Hi all,
>
> This is the proposal for a new object called MediaController.
Yay! I hadn't seen this thread until just now. But coincidentally I've
spent some time on this issue too recently thanks Kevin filing
https://bugzilla.mozilla.org/show_bug.cgi?id=1084464
> Use cases
> =========
>
> * I have a media player app, and I want to use the media keys on my keyboard on desktop to control it.
>
> * I have a media player app and I want to use the headset controls on my headphones to control it.
>
> * I have a media player app and I want to use the mobile soft keys (e.g. as done on iOS and Android lock screens) to control it.
I'd like to also add the following use cases:
* I have a media player app and I want to show information about the
currently playing song on the lock screen.
* I have a homescreen app and I want it to show information about the
currently playing song.
* I have a media player app and I want it to pause audio when there's
an incoming phone call, and resume the audio once the phone call is
over.
* I have a media player app and I want it to pause audio when the user
starts watching a video in YouTube or another media player app.
There's also a somewhat more controversial:
* I have a media player app and I want it to keep playing music when
the user switches away to another app, even on platforms where apps
are normally muted when the user switches away.
> Possible future use cases
> =========================
>
> * I have registered a media player app and I want it to start up when I press the play key. (We could possibly dispatch an event to the SW, etc., out of scope for now)
Oh, interesting! But I agree that we can leave this one for later.
> [NoInterfaceObject]
> interface NavigatorMediaController {
> Promise<MediaController> requestMediaController();
> };
>
> Navigator implements NavigatorMediaController;
> enum MediaKeyEventType {
> "play",
> "pause",
> "playpause",
> "next",
> "previous",
> // possibly other codes
> };
We need "stop" as well. This usually rewinds to the beginning of the
current song. I don't know how commonly used it is these days, but I
think some hardware keyboards still have it separate from the "pause"
button.
Also, would it be possible to fire "play" and "pause" events rather
than "playpause" events? Could we use the MediaController.mediaActive
property to determine which one to fire?
> dictionary MediaKeyEventInit : EventInit {
> MediaKeyEventType detail = "play";
> };
>
> [Constructor(DOMString type, optional MediaKeyEventInit init)]
> interface MediaKeyEvent : Event {
> readonly attribute MediaKeyEventType detail;
> };
>
> interface MediaController : EventTarget {
> attribute EventHandler onmediakey;
> // Do we need a revoke method?
> // void revoke();
> // This attribute is used to see if the play/pause event has been received correct.
> attribute boolean mediaActive;
>
> // An image to show when the device is locked.
> attribute (DOMString or URL or Blob or HTMLImageElement or HTMLCanvasElement or HTMLVideoElement) mediaImage;
I'd simplify this and only enable passing a DOMString (url) or Blob
here. URL objects automatically stringify to a useable url.
I don't see a reason why passing a HTMLImageElement or
HTMLVideoElement is needed given that they are always loaded from
URLs. And I don't think the use cases for dynamically generated images
are strong enough that we couldn't ask developers to turn the
HTMLCanvasElement into a Blob.
> // Extra info to show.
> attribute DOMString mediaTitle;
> attribute DOMString mediaDuration;
> // other attributes.
We also need the current position so that we can show that on a lockscreen.
Not sure if we should add a "attribute double currentMediaTime;" which
the platform would automatically increase as long as mediaActive is
set to true. Alternatively we could add two functions like:
indicatePlaying((DOMString or Blob) image, DOMString title, duration,
position); // All arguments would be optional
indicateNotPlaying();
We might also want to allow the page to indicate that it's currently
buffering audio. This could be useful for streaming services so that
they can reflect in the lockscreen UI why audio isn't playing. Adding
something like "attribute boolean buffering" would cover that.
Regarding the "pause while on a phone call" use case, I think most
mobile platforms would want to forcefully pause any application audio
when there's an incoming phone call. All of FirefoxOS, Chrome for
Android and Safario for iOS does this. I think Android automatically
mutes Fennec, but I'm not sure if Fennec in turn pauses any webpage
audio.
So I think we should forcefully pause any <audio>/<video>/WebAudio audio.
In addition we could fire some form of "interrupted"/"resumed" events
on the MediaController object.
This would also cover the "pause when playing in youtube" use case. We
could do essentially exactly what we're doing today using the
mozaudiochannel=content policy. But treating any audio as
channel=content from any app which has
MediaController.mediaActive=true.
> Open questions
> ==============
>
> The MediaKey* terminology is closed to what is used in the EME spec. ehsan thinks this is fine because it is not likely for most apps to want to use EME, so there are no big chances for confusion.
I don't really have an opinion.
> Is it OK to diverge from the DOM KeyboardEvent codes for this?
*I* think so, but I'm sure others might disagree. I think we should
propose this spec to W3C and then we can see what other browser
vendors think.
> The policy choice as to what to do when two web apps request access to this API is left to the UA, and the UA has the freedom to adopt their own policies. Is that OK? (ehsan thinks yes.)
I think so yes.
> As far as the ergonomics of using the API is concerned, should we return the same MediaController object from requestMediaKeys() no matter how many times the author calls it?
I think that if we return different instances then those instances
should act independently. It might be easier to simply always return
the same instance. But I don't feel strongly.
/ Jonas