Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright (C) 2008, 2009, 2010, 2011 Apple Inc. All rights reserved. | 2 * Copyright (C) 2008, 2009, 2010, 2011 Apple Inc. All rights reserved. |
| 3 * Copyright (C) 2012 Google Inc. All rights reserved. | 3 * Copyright (C) 2012 Google Inc. All rights reserved. |
| 4 * | 4 * |
| 5 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
| 6 * modification, are permitted provided that the following conditions | 6 * modification, are permitted provided that the following conditions |
| 7 * are met: | 7 * are met: |
| 8 * | 8 * |
| 9 * 1. Redistributions of source code must retain the above copyright | 9 * 1. Redistributions of source code must retain the above copyright |
| 10 * notice, this list of conditions and the following disclaimer. | 10 * notice, this list of conditions and the following disclaimer. |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 25 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 25 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| 26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF | 26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
| 27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| 28 */ | 28 */ |
| 29 | 29 |
| 30 #include "core/html/shadow/MediaControlElements.h" | 30 #include "core/html/shadow/MediaControlElements.h" |
| 31 | 31 |
| 32 #include "bindings/core/v8/ExceptionStatePlaceholder.h" | 32 #include "bindings/core/v8/ExceptionStatePlaceholder.h" |
| 33 #include "core/InputTypeNames.h" | 33 #include "core/InputTypeNames.h" |
| 34 #include "core/dom/ClientRect.h" | 34 #include "core/dom/ClientRect.h" |
| 35 #include "core/dom/DOMTokenList.h" | |
|
fs
2016/02/23 13:16:43
What needs this?
srivats
2016/02/24 05:20:17
Removed the stale import
| |
| 36 #include "core/dom/Document.h" | |
| 37 #include "core/dom/Element.h" | |
| 38 #include "core/dom/Text.h" | |
| 35 #include "core/dom/shadow/ShadowRoot.h" | 39 #include "core/dom/shadow/ShadowRoot.h" |
| 36 #include "core/events/MouseEvent.h" | 40 #include "core/events/MouseEvent.h" |
| 37 #include "core/frame/LocalFrame.h" | 41 #include "core/frame/LocalFrame.h" |
| 42 #include "core/html/HTMLHeadingElement.h" | |
| 43 #include "core/html/HTMLLabelElement.h" | |
| 44 #include "core/html/HTMLSpanElement.h" | |
| 38 #include "core/html/HTMLVideoElement.h" | 45 #include "core/html/HTMLVideoElement.h" |
| 39 #include "core/html/TimeRanges.h" | 46 #include "core/html/TimeRanges.h" |
| 40 #include "core/html/shadow/MediaControls.h" | 47 #include "core/html/shadow/MediaControls.h" |
| 48 #include "core/html/track/TextTrackList.h" | |
| 41 #include "core/input/EventHandler.h" | 49 #include "core/input/EventHandler.h" |
| 42 #include "core/layout/LayoutSlider.h" | 50 #include "core/layout/LayoutSlider.h" |
| 43 #include "core/layout/LayoutTheme.h" | 51 #include "core/layout/LayoutTheme.h" |
| 44 #include "core/layout/LayoutVideo.h" | 52 #include "core/layout/LayoutVideo.h" |
| 53 #include "platform/EventDispatchForbiddenScope.h" | |
| 45 #include "platform/RuntimeEnabledFeatures.h" | 54 #include "platform/RuntimeEnabledFeatures.h" |
| 55 #include "platform/text/PlatformLocale.h" | |
| 46 #include "public/platform/Platform.h" | 56 #include "public/platform/Platform.h" |
| 47 | 57 |
| 48 namespace blink { | 58 namespace blink { |
| 49 | 59 |
| 50 using namespace HTMLNames; | 60 using namespace HTMLNames; |
| 51 | 61 |
| 52 namespace { | 62 namespace { |
| 53 | 63 |
| 54 // This is the duration from mediaControls.css | 64 // This is the duration from mediaControls.css |
| 55 const double fadeOutDuration = 0.3; | 65 const double fadeOutDuration = 0.3; |
| 56 | 66 |
| 67 // Save the track index in an attribute to avoid holding a pointer to the text t rack element. | |
| 68 static const char trackIndexAttr[] = "data-track-index"; | |
| 69 | |
| 70 // When specified as trackIndex, disable text tracks. | |
| 71 static const int trackIndexOffValue = -1; | |
| 72 | |
| 57 bool isUserInteractionEvent(Event* event) | 73 bool isUserInteractionEvent(Event* event) |
| 58 { | 74 { |
| 59 const AtomicString& type = event->type(); | 75 const AtomicString& type = event->type(); |
| 60 return type == EventTypeNames::mousedown | 76 return type == EventTypeNames::mousedown |
| 61 || type == EventTypeNames::mouseup | 77 || type == EventTypeNames::mouseup |
| 62 || type == EventTypeNames::click | 78 || type == EventTypeNames::click |
| 63 || type == EventTypeNames::dblclick | 79 || type == EventTypeNames::dblclick |
| 64 || event->isKeyboardEvent() | 80 || event->isKeyboardEvent() |
| 65 || event->isTouchEvent(); | 81 || event->isTouchEvent(); |
| 66 } | 82 } |
| (...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 346 button->setType(InputTypeNames::button); | 362 button->setType(InputTypeNames::button); |
| 347 button->setShadowPseudoId(AtomicString("-webkit-media-controls-toggle-closed -captions-button", AtomicString::ConstructFromLiteral)); | 363 button->setShadowPseudoId(AtomicString("-webkit-media-controls-toggle-closed -captions-button", AtomicString::ConstructFromLiteral)); |
| 348 button->setIsWanted(false); | 364 button->setIsWanted(false); |
| 349 return button.release(); | 365 return button.release(); |
| 350 } | 366 } |
| 351 | 367 |
| 352 void MediaControlToggleClosedCaptionsButtonElement::updateDisplayType() | 368 void MediaControlToggleClosedCaptionsButtonElement::updateDisplayType() |
| 353 { | 369 { |
| 354 bool captionsVisible = mediaElement().closedCaptionsVisible(); | 370 bool captionsVisible = mediaElement().closedCaptionsVisible(); |
| 355 setDisplayType(captionsVisible ? MediaHideClosedCaptionsButton : MediaShowCl osedCaptionsButton); | 371 setDisplayType(captionsVisible ? MediaHideClosedCaptionsButton : MediaShowCl osedCaptionsButton); |
| 356 setChecked(captionsVisible); | |
| 357 } | 372 } |
| 358 | 373 |
| 359 void MediaControlToggleClosedCaptionsButtonElement::defaultEventHandler(Event* e vent) | 374 void MediaControlToggleClosedCaptionsButtonElement::defaultEventHandler(Event* e vent) |
| 360 { | 375 { |
| 361 if (event->type() == EventTypeNames::click) { | 376 if (event->type() == EventTypeNames::click) { |
| 362 mediaElement().setClosedCaptionsVisible(!mediaElement().closedCaptionsVi sible()); | 377 mediaControls().toggleTextTrackList(); |
| 363 setChecked(mediaElement().closedCaptionsVisible()); | |
| 364 updateDisplayType(); | 378 updateDisplayType(); |
| 365 event->setDefaultHandled(); | 379 event->setDefaultHandled(); |
| 366 } | 380 } |
| 367 | 381 |
| 368 HTMLInputElement::defaultEventHandler(event); | 382 HTMLInputElement::defaultEventHandler(event); |
| 369 } | 383 } |
| 370 | 384 |
| 371 // ---------------------------- | 385 // ---------------------------- |
| 372 | 386 |
| 387 MediaControlTextTrackListElement::MediaControlTextTrackListElement(MediaControls & mediaControls) | |
| 388 : MediaControlDivElement(mediaControls, MediaTextTrackList) | |
| 389 { | |
| 390 } | |
| 391 | |
| 392 PassRefPtrWillBeRawPtr<MediaControlTextTrackListElement> MediaControlTextTrackLi stElement::create(MediaControls& mediaControls) | |
| 393 { | |
| 394 RefPtrWillBeRawPtr<MediaControlTextTrackListElement> element = | |
| 395 adoptRefWillBeNoop(new MediaControlTextTrackListElement(mediaControls)); | |
| 396 element->setShadowPseudoId(AtomicString("-internal-media-controls-text-track -list", | |
| 397 AtomicString::ConstructFromLiteral)); | |
| 398 element->setIsWanted(false); | |
| 399 return element.release(); | |
| 400 } | |
| 401 | |
| 402 void MediaControlTextTrackListElement::defaultEventHandler(Event* event) | |
| 403 { | |
| 404 if (event->type() == EventTypeNames::change) { | |
| 405 // Identify which input element was selected and set track to showing | |
| 406 Node* target = event->target()->toNode(); | |
| 407 if (!target || !target->isElementNode()) | |
| 408 return; | |
| 409 | |
| 410 bool validIndex; | |
| 411 int trackIndex = toElement(target)->getAttribute(trackIndexAttr).toInt(& validIndex); | |
|
fs
2016/02/23 13:16:44
getIntegralAttribute
(loses the validity checking
srivats
2016/02/24 05:20:17
Done.
| |
| 412 ASSERT(validIndex); | |
| 413 if (trackIndex != trackIndexOffValue) { | |
|
fs
2016/02/23 13:16:43
Nit: { } not needed
srivats
2016/02/24 05:20:17
Done.
| |
| 414 showTextTrackAtIndex(trackIndex); | |
| 415 } else { | |
| 416 disableTextTracks(); | |
| 417 } | |
| 418 | |
| 419 mediaControls().toggleTextTrackList(); | |
| 420 event->setDefaultHandled(); | |
| 421 } | |
| 422 HTMLDivElement::defaultEventHandler(event); | |
|
fs
2016/02/23 13:16:44
MediaControlDivElement (unless there's a reason to
srivats
2016/02/24 05:20:17
Done.
| |
| 423 } | |
| 424 | |
| 425 void MediaControlTextTrackListElement::showTextTrackAtIndex(unsigned indexToEnab le) | |
| 426 { | |
| 427 disableTextTracks(); | |
|
fs
2016/02/23 13:16:44
Could we hoist this out into callers instead? (Els
srivats
2016/02/24 05:20:17
Done.
| |
| 428 TextTrackList* trackList = mediaElement().textTracks(); | |
| 429 if (trackList && trackList->length() == 0) | |
|
fs
2016/02/23 13:16:44
I guess you want: !trackList || trackList->length(
srivats
2016/02/24 05:20:17
Done.
| |
| 430 return; | |
| 431 if (indexToEnable >= trackList->length()) | |
| 432 return; | |
| 433 TextTrack* track = trackList->anonymousIndexedGetter(indexToEnable); | |
| 434 if (track && track->isRenderable()) | |
|
fs
2016/02/23 13:16:44
Since we know indexToEnable is in range, the null-
srivats
2016/02/24 05:20:17
Done.
| |
| 435 track->setMode(TextTrack::showingKeyword()); | |
| 436 mediaElement().disableAutomaticTextTrackSelection(); | |
|
fs
2016/02/23 13:16:43
It could make sense to do this in the caller too (
srivats
2016/02/24 05:20:17
Done.
| |
| 437 } | |
| 438 | |
| 439 void MediaControlTextTrackListElement::disableTextTracks() | |
|
fs
2016/02/23 13:16:44
disableShowingTextTracks?
srivats
2016/02/24 05:20:17
Done.
| |
| 440 { | |
| 441 TextTrackList* trackList = mediaElement().textTracks(); | |
| 442 for (unsigned i = 0; i < trackList->length(); ++i) { | |
| 443 TextTrack* track = trackList->anonymousIndexedGetter(i); | |
| 444 if (track->mode() != TextTrack::hiddenKeyword()) | |
| 445 track->setMode(TextTrack::disabledKeyword()); | |
| 446 } | |
| 447 } | |
| 448 | |
| 449 String MediaControlTextTrackListElement::getTextTrackLabel(TextTrack* track) | |
| 450 { | |
| 451 if (!track) | |
| 452 return mediaElement().locale().queryString(WebLocalizedString::TextTrack sOff); | |
| 453 | |
| 454 String trackLabel = track->label(); | |
| 455 | |
| 456 if (trackLabel.isEmpty()) | |
| 457 trackLabel = track->language(); | |
| 458 | |
| 459 if (trackLabel.isEmpty()) | |
| 460 trackLabel = String(mediaElement().locale().queryString(WebLocalizedStri ng::TextTracksNoLabel)); | |
| 461 | |
| 462 return trackLabel; | |
| 463 } | |
| 464 | |
| 465 // TextTrack parameter when passed in as a nullptr, creates the "Off" list item in the track list. | |
| 466 PassRefPtrWillBeRawPtr<Element> MediaControlTextTrackListElement::createTextTrac kListItem(TextTrack* track) | |
| 467 { | |
| 468 Document& document = this->document(); | |
| 469 int trackIndex = track ? track->trackIndex() : trackIndexOffValue; | |
| 470 RefPtrWillBeRawPtr<HTMLLabelElement> trackItem = HTMLLabelElement::create(do cument, 0); | |
| 471 trackItem->setShadowPseudoId(AtomicString("-internal-media-controls-text-tra ck-list-item", | |
| 472 AtomicString::ConstructFromLiteral)); | |
| 473 RefPtrWillBeRawPtr<HTMLInputElement> trackItemInput = HTMLInputElement::crea te(document, 0, false); | |
| 474 trackItemInput->setShadowPseudoId(AtomicString("-internal-media-controls-tex t-track-list-item-input", | |
| 475 AtomicString::ConstructFromLiteral)); | |
| 476 trackItemInput->setType(InputTypeNames::radio); | |
| 477 trackItemInput->setAttribute(trackIndexAttr, AtomicString::number(trackIndex ), ASSERT_NO_EXCEPTION); | |
|
fs
2016/02/23 13:16:43
setIntegralAttribute
srivats
2016/02/24 05:20:17
Done.
| |
| 478 if (!mediaElement().closedCaptionsVisible()) { | |
| 479 if (!track) | |
| 480 trackItemInput->setChecked(true); | |
| 481 } else { | |
| 482 // If there are multiple text tracks set to showing, they must all have | |
| 483 // checkmarks displayed. | |
| 484 if (track && track->mode() == TextTrack::showingKeyword()) | |
| 485 trackItemInput->setChecked(true); | |
| 486 } | |
| 487 RefPtrWillBeRawPtr<HTMLSpanElement> trackKindMarker = HTMLSpanElement::creat e(document); | |
| 488 if (track && track->kind() == track->captionsKeyword()) { | |
| 489 trackKindMarker->setShadowPseudoId(AtomicString("-internal-media-control s-text-track-list-kind-captions", | |
| 490 AtomicString::ConstructFromLiteral)); | |
| 491 } else if (track && track->kind() == track->subtitlesKeyword()) { | |
| 492 trackKindMarker->setShadowPseudoId(AtomicString("-internal-media-control s-text-track-list-kind-subtitles", | |
| 493 AtomicString::ConstructFromLiteral)); | |
| 494 } | |
| 495 trackItem->appendChild(trackItemInput); | |
| 496 trackItem->appendChild(Text::create(document, getTextTrackLabel(track))); | |
| 497 trackItem->appendChild(trackKindMarker); | |
| 498 return trackItem; | |
| 499 } | |
| 500 | |
| 501 void MediaControlTextTrackListElement::refreshTextTrackListMenu() | |
| 502 { | |
| 503 if (!mediaElement().hasClosedCaptions() || !mediaElement().textTracksAreRead y()) | |
| 504 return; | |
| 505 | |
| 506 removeChildren(); | |
|
fs
2016/02/23 13:16:44
removeChildren(OmitSubtreeModifiedEvent)
I'm gues
srivats
2016/02/24 05:20:17
Done.
| |
| 507 | |
| 508 // Construct a menu for subtitles and captions | |
| 509 EventDispatchForbiddenScope::AllowUserAgentEvents allowEvents; | |
| 510 Document& document = this->document(); | |
|
fs
2016/02/23 13:16:43
Could just use document() directly in the single p
srivats
2016/02/24 05:20:17
Done.
| |
| 511 RefPtrWillBeRawPtr<HTMLDivElement> tracksSection = HTMLDivElement::create(do cument); | |
| 512 tracksSection->setAttribute(roleAttr, radiogroupAttr.localName()); | |
|
fs
2016/02/23 13:16:43
I'm on the fence on whether this is "too smart" or
| |
| 513 // Pass in a nullptr to createTextTrackListItem to create the "Off" track it em. | |
| 514 tracksSection->appendChild(createTextTrackListItem(nullptr)); | |
| 515 | |
| 516 TextTrackList* trackList = mediaElement().textTracks(); | |
| 517 for (unsigned i = 0; i < trackList->length(); i++) { | |
| 518 TextTrack* track = trackList->anonymousIndexedGetter(i); | |
| 519 if (!track->isRenderable()) | |
| 520 continue; | |
| 521 RefPtrWillBeRawPtr<Element> trackItem = createTextTrackListItem(track); | |
|
fs
2016/02/23 13:16:43
No need for this temporary.
srivats
2016/02/24 05:20:17
Done.
| |
| 522 tracksSection->appendChild(trackItem); | |
| 523 } | |
| 524 appendChild(tracksSection); | |
| 525 } | |
| 526 | |
| 527 // ---------------------------- | |
| 528 | |
| 373 MediaControlTimelineElement::MediaControlTimelineElement(MediaControls& mediaCon trols) | 529 MediaControlTimelineElement::MediaControlTimelineElement(MediaControls& mediaCon trols) |
| 374 : MediaControlInputElement(mediaControls, MediaSlider) | 530 : MediaControlInputElement(mediaControls, MediaSlider) |
| 375 { | 531 { |
| 376 } | 532 } |
| 377 | 533 |
| 378 PassRefPtrWillBeRawPtr<MediaControlTimelineElement> MediaControlTimelineElement: :create(MediaControls& mediaControls) | 534 PassRefPtrWillBeRawPtr<MediaControlTimelineElement> MediaControlTimelineElement: :create(MediaControls& mediaControls) |
| 379 { | 535 { |
| 380 RefPtrWillBeRawPtr<MediaControlTimelineElement> timeline = adoptRefWillBeNoo p(new MediaControlTimelineElement(mediaControls)); | 536 RefPtrWillBeRawPtr<MediaControlTimelineElement> timeline = adoptRefWillBeNoo p(new MediaControlTimelineElement(mediaControls)); |
| 381 timeline->ensureUserAgentShadowRoot(); | 537 timeline->ensureUserAgentShadowRoot(); |
| 382 timeline->setType(InputTypeNames::range); | 538 timeline->setType(InputTypeNames::range); |
| (...skipping 265 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 648 } | 804 } |
| 649 | 805 |
| 650 PassRefPtrWillBeRawPtr<MediaControlCurrentTimeDisplayElement> MediaControlCurren tTimeDisplayElement::create(MediaControls& mediaControls) | 806 PassRefPtrWillBeRawPtr<MediaControlCurrentTimeDisplayElement> MediaControlCurren tTimeDisplayElement::create(MediaControls& mediaControls) |
| 651 { | 807 { |
| 652 RefPtrWillBeRawPtr<MediaControlCurrentTimeDisplayElement> element = adoptRef WillBeNoop(new MediaControlCurrentTimeDisplayElement(mediaControls)); | 808 RefPtrWillBeRawPtr<MediaControlCurrentTimeDisplayElement> element = adoptRef WillBeNoop(new MediaControlCurrentTimeDisplayElement(mediaControls)); |
| 653 element->setShadowPseudoId(AtomicString("-webkit-media-controls-current-time -display", AtomicString::ConstructFromLiteral)); | 809 element->setShadowPseudoId(AtomicString("-webkit-media-controls-current-time -display", AtomicString::ConstructFromLiteral)); |
| 654 return element.release(); | 810 return element.release(); |
| 655 } | 811 } |
| 656 | 812 |
| 657 } // namespace blink | 813 } // namespace blink |
| OLD | NEW |