Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1809)

Side by Side Diff: Source/core/html/track/TextTrackCue.cpp

Issue 77853002: Move VTT functionality from TextTrackCue.* to VTTCue.* (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Address nits. Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « Source/core/html/track/TextTrackCue.h ('k') | Source/core/html/track/vtt/VTTCue.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2011 Google Inc. All rights reserved. 2 * Copyright (C) 2011 Google Inc. All rights reserved.
3 * Copyright (C) 2011, 2012, 2013 Apple Inc. All rights reserved. 3 * Copyright (C) 2011, 2012, 2013 Apple 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 are 6 * modification, are permitted provided that the following conditions are
7 * met: 7 * met:
8 * 8 *
9 * * Redistributions of source code must retain the above copyright 9 * * 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
25 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 25 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */ 30 */
31 31
32 #include "config.h" 32 #include "config.h"
33 #include "core/html/track/TextTrackCue.h" 33 #include "core/html/track/TextTrackCue.h"
34 34
35 #include "CSSPropertyNames.h"
36 #include "CSSValueKeywords.h"
37 #include "RuntimeEnabledFeatures.h"
38 #include "bindings/v8/ExceptionMessages.h" 35 #include "bindings/v8/ExceptionMessages.h"
39 #include "bindings/v8/ExceptionState.h"
40 #include "bindings/v8/ExceptionStatePlaceholder.h" 36 #include "bindings/v8/ExceptionStatePlaceholder.h"
41 #include "core/dom/DocumentFragment.h"
42 #include "core/events/Event.h" 37 #include "core/events/Event.h"
43 #include "core/dom/NodeTraversal.h"
44 #include "core/html/HTMLDivElement.h" 38 #include "core/html/HTMLDivElement.h"
45 #include "core/html/track/TextTrack.h" 39 #include "core/html/track/TextTrack.h"
46 #include "core/html/track/TextTrackCueList.h" 40 #include "core/html/track/TextTrackCueList.h"
47 #include "core/html/track/vtt/VTTElement.h"
48 #include "core/html/track/vtt/VTTParser.h"
49 #include "core/html/track/vtt/VTTRegionList.h"
50 #include "core/rendering/RenderTextTrackCue.h"
51 #include "wtf/MathExtras.h"
52 #include "wtf/text/StringBuilder.h"
53 41
54 namespace WebCore { 42 namespace WebCore {
55 43
56 static const int invalidCueIndex = -1; 44 static const int invalidCueIndex = -1;
57 static const int undefinedPosition = -1;
58 45
59 static const CSSValueID displayWritingModeMap[] = { 46 // ----------------------------
60 CSSValueHorizontalTb, CSSValueVerticalRl, CSSValueVerticalLr
61 };
62 COMPILE_ASSERT(WTF_ARRAY_LENGTH(displayWritingModeMap) == TextTrackCue::NumberOf WritingDirections,
63 displayWritingModeMap_has_wrong_size);
64 47
65 static const CSSValueID displayAlignmentMap[] = { 48 TextTrackCueBox::TextTrackCueBox(Document& document)
66 CSSValueStart, CSSValueCenter, CSSValueEnd, CSSValueLeft, CSSValueRight 49 : HTMLDivElement(document)
67 };
68 COMPILE_ASSERT(WTF_ARRAY_LENGTH(displayAlignmentMap) == TextTrackCue::NumberOfAl ignments,
69 displayAlignmentMap_has_wrong_size);
70
71 static const String& startKeyword()
72 { 50 {
73 DEFINE_STATIC_LOCAL(const String, start, ("start"));
74 return start;
75 } 51 }
76 52
77 static const String& middleKeyword() 53 // ----------------------------
78 {
79 DEFINE_STATIC_LOCAL(const String, middle, ("middle"));
80 return middle;
81 }
82 54
83 static const String& endKeyword() 55 bool TextTrackCue::isInfiniteOrNonNumber(double value, const char* method, Excep tionState& exceptionState)
84 {
85 DEFINE_STATIC_LOCAL(const String, end, ("end"));
86 return end;
87 }
88
89 static const String& leftKeyword()
90 {
91 DEFINE_STATIC_LOCAL(const String, left, ("left"));
92 return left;
93 }
94
95 static const String& rightKeyword()
96 {
97 DEFINE_STATIC_LOCAL(const String, right, ("right"));
98 return right;
99 }
100
101 static const String& horizontalKeyword()
102 {
103 return emptyString();
104 }
105
106 static const String& verticalGrowingLeftKeyword()
107 {
108 DEFINE_STATIC_LOCAL(const String, verticalrl, ("rl"));
109 return verticalrl;
110 }
111
112 static const String& verticalGrowingRightKeyword()
113 {
114 DEFINE_STATIC_LOCAL(const String, verticallr, ("lr"));
115 return verticallr;
116 }
117
118 static bool isInfiniteOrNonNumber(double value, const char* method, ExceptionSta te& exceptionState)
119 { 56 {
120 if (std::isinf(value)) { 57 if (std::isinf(value)) {
121 exceptionState.throwTypeError(ExceptionMessages::failedToSet(method, "Te xtTrackCue", "The value provided is infinite.")); 58 exceptionState.throwTypeError(ExceptionMessages::failedToSet(method, "Te xtTrackCue", "The value provided is infinite."));
122 return true; 59 return true;
123 } 60 }
124 if (std::isnan(value)) { 61 if (std::isnan(value)) {
125 exceptionState.throwTypeError(ExceptionMessages::failedToSet(method, "Te xtTrackCue", "The value provided is not a number.")); 62 exceptionState.throwTypeError(ExceptionMessages::failedToSet(method, "Te xtTrackCue", "The value provided is not a number."));
126 return true; 63 return true;
127 } 64 }
128 return false; 65 return false;
129 } 66 }
130 67
131 static bool isInvalidPercentage(double value, const char* method, ExceptionState & exceptionState) 68 TextTrackCue::TextTrackCue(double start, double end)
132 {
133 if (isInfiniteOrNonNumber(value, method, exceptionState))
134 return true;
135 if (value < 0 || value > 100) {
136 exceptionState.throwDOMException(IndexSizeError, ExceptionMessages::fail edToSet(method, "TextTrackCue", "The value provided (" + String::number(value) + ") is not between 0 and 100."));
137 return true;
138 }
139 return false;
140 }
141
142
143 // ----------------------------
144
145 TextTrackCueBox::TextTrackCueBox(Document& document, TextTrackCue* cue)
146 : HTMLDivElement(document)
147 , m_cue(cue)
148 {
149 setPart(textTrackCueBoxShadowPseudoId());
150 }
151
152 TextTrackCue* TextTrackCueBox::getCue() const
153 {
154 return m_cue;
155 }
156
157 void TextTrackCueBox::applyCSSProperties(const IntSize&)
158 {
159 // FIXME: Apply all the initial CSS positioning properties. http://wkb.ug/79 916
160 if (!m_cue->regionId().isEmpty()) {
161 setInlineStyleProperty(CSSPropertyPosition, CSSValueRelative);
162 return;
163 }
164
165 // 3.5.1 On the (root) List of WebVTT Node Objects:
166
167 // the 'position' property must be set to 'absolute'
168 setInlineStyleProperty(CSSPropertyPosition, CSSValueAbsolute);
169
170 // the 'unicode-bidi' property must be set to 'plaintext'
171 setInlineStyleProperty(CSSPropertyUnicodeBidi, CSSValueWebkitPlaintext);
172
173 // the 'direction' property must be set to direction
174 setInlineStyleProperty(CSSPropertyDirection, m_cue->getCSSWritingDirection() );
175
176 // the 'writing-mode' property must be set to writing-mode
177 setInlineStyleProperty(CSSPropertyWebkitWritingMode, m_cue->getCSSWritingMod e());
178
179 std::pair<float, float> position = m_cue->getCSSPosition();
180
181 // the 'top' property must be set to top,
182 setInlineStyleProperty(CSSPropertyTop, position.second, CSSPrimitiveValue::C SS_PERCENTAGE);
183
184 // the 'left' property must be set to left
185 setInlineStyleProperty(CSSPropertyLeft, position.first, CSSPrimitiveValue::C SS_PERCENTAGE);
186
187 // the 'width' property must be set to width, and the 'height' property mus t be set to height
188 if (m_cue->vertical() == horizontalKeyword()) {
189 setInlineStyleProperty(CSSPropertyWidth, static_cast<double>(m_cue->getC SSSize()), CSSPrimitiveValue::CSS_PERCENTAGE);
190 setInlineStyleProperty(CSSPropertyHeight, CSSValueAuto);
191 } else {
192 setInlineStyleProperty(CSSPropertyWidth, CSSValueAuto);
193 setInlineStyleProperty(CSSPropertyHeight, static_cast<double>(m_cue->get CSSSize()), CSSPrimitiveValue::CSS_PERCENTAGE);
194 }
195
196 // The 'text-align' property on the (root) List of WebVTT Node Objects must
197 // be set to the value in the second cell of the row of the table below
198 // whose first cell is the value of the corresponding cue's text track cue
199 // alignment:
200 setInlineStyleProperty(CSSPropertyTextAlign, m_cue->getCSSAlignment());
201
202 if (!m_cue->snapToLines()) {
203 // 10.13.1 Set up x and y:
204 // Note: x and y are set through the CSS left and top above.
205
206 // 10.13.2 Position the boxes in boxes such that the point x% along the
207 // width of the bounding box of the boxes in boxes is x% of the way
208 // across the width of the video's rendering area, and the point y%
209 // along the height of the bounding box of the boxes in boxes is y%
210 // of the way across the height of the video's rendering area, while
211 // maintaining the relative positions of the boxes in boxes to each
212 // other.
213 setInlineStyleProperty(CSSPropertyWebkitTransform,
214 String::format("translate(-%.2f%%, -%.2f%%)", position.first, po sition.second));
215
216 setInlineStyleProperty(CSSPropertyWhiteSpace, CSSValuePre);
217 }
218 }
219
220 const AtomicString& TextTrackCueBox::textTrackCueBoxShadowPseudoId()
221 {
222 DEFINE_STATIC_LOCAL(const AtomicString, trackDisplayBoxShadowPseudoId, ("-we bkit-media-text-track-display", AtomicString::ConstructFromLiteral));
223 return trackDisplayBoxShadowPseudoId;
224 }
225
226 RenderObject* TextTrackCueBox::createRenderer(RenderStyle*)
227 {
228 return new RenderTextTrackCue(this);
229 }
230
231 // ----------------------------
232
233 TextTrackCue::TextTrackCue(Document& document, double start, double end, const S tring& content)
234 : m_startTime(start) 69 : m_startTime(start)
235 , m_endTime(end) 70 , m_endTime(end)
236 , m_content(content)
237 , m_linePosition(undefinedPosition)
238 , m_computedLinePosition(undefinedPosition)
239 , m_textPosition(50)
240 , m_cueSize(100)
241 , m_cueIndex(invalidCueIndex) 71 , m_cueIndex(invalidCueIndex)
242 , m_writingDirection(Horizontal)
243 , m_cueAlignment(Middle)
244 , m_webVTTNodeTree(0)
245 , m_track(0) 72 , m_track(0)
246 , m_isActive(false) 73 , m_isActive(false)
247 , m_pauseOnExit(false) 74 , m_pauseOnExit(false)
248 , m_snapToLines(true)
249 , m_cueBackgroundBox(HTMLDivElement::create(document))
250 , m_displayTreeShouldChange(true)
251 , m_displayDirection(CSSValueLtr)
252 , m_notifyRegion(true)
253 { 75 {
254 } 76 }
255 77
256 TextTrackCue::~TextTrackCue() 78 String TextTrackCue::toString() const
257 { 79 {
258 displayTreeInternal()->remove(ASSERT_NO_EXCEPTION); 80 return String::format("%p id=%s interval=%f-->%f)", this, id().utf8().data() , startTime(), endTime());
259 }
260
261 PassRefPtr<TextTrackCueBox> TextTrackCue::displayTreeInternal()
262 {
263 if (!m_displayTree)
264 m_displayTree = TextTrackCueBox::create(document(), this);
265 return m_displayTree;
266 } 81 }
267 82
268 void TextTrackCue::cueWillChange() 83 void TextTrackCue::cueWillChange()
269 { 84 {
270 if (m_track) 85 if (m_track)
271 m_track->cueWillChange(this); 86 m_track->cueWillChange(this);
272 } 87 }
273 88
274 void TextTrackCue::cueDidChange() 89 void TextTrackCue::cueDidChange()
275 { 90 {
276 if (m_track) 91 if (m_track)
277 m_track->cueDidChange(this); 92 m_track->cueDidChange(this);
278
279 m_displayTreeShouldChange = true;
280 } 93 }
281 94
282 TextTrack* TextTrackCue::track() const 95 TextTrack* TextTrackCue::track() const
283 { 96 {
284 return m_track; 97 return m_track;
285 } 98 }
286 99
287 void TextTrackCue::setTrack(TextTrack* track) 100 void TextTrackCue::setTrack(TextTrack* track)
288 { 101 {
289 m_track = track; 102 m_track = track;
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
332 void TextTrackCue::setPauseOnExit(bool value) 145 void TextTrackCue::setPauseOnExit(bool value)
333 { 146 {
334 if (m_pauseOnExit == value) 147 if (m_pauseOnExit == value)
335 return; 148 return;
336 149
337 cueWillChange(); 150 cueWillChange();
338 m_pauseOnExit = value; 151 m_pauseOnExit = value;
339 cueDidChange(); 152 cueDidChange();
340 } 153 }
341 154
342 const String& TextTrackCue::vertical() const
343 {
344 switch (m_writingDirection) {
345 case Horizontal:
346 return horizontalKeyword();
347 case VerticalGrowingLeft:
348 return verticalGrowingLeftKeyword();
349 case VerticalGrowingRight:
350 return verticalGrowingRightKeyword();
351 default:
352 ASSERT_NOT_REACHED();
353 return emptyString();
354 }
355 }
356
357 void TextTrackCue::setVertical(const String& value, ExceptionState& exceptionSta te)
358 {
359 // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-ele ment.html#dom-texttrackcue-vertical
360 // On setting, the text track cue writing direction must be set to the value given
361 // in the first cell of the row in the table above whose second cell is a
362 // case-sensitive match for the new value, if any. If none of the values mat ch, then
363 // the user agent must instead throw a SyntaxError exception.
364
365 WritingDirection direction = m_writingDirection;
366 if (value == horizontalKeyword())
367 direction = Horizontal;
368 else if (value == verticalGrowingLeftKeyword())
369 direction = VerticalGrowingLeft;
370 else if (value == verticalGrowingRightKeyword())
371 direction = VerticalGrowingRight;
372 else
373 exceptionState.throwDOMException(SyntaxError, ExceptionMessages::failedT oSet("vertical", "TextTrackCue", "The value provided ('" + value + "') is invali d. Only 'rl', 'lr', and the empty string are accepted."));
374
375 if (direction == m_writingDirection)
376 return;
377
378 cueWillChange();
379 m_writingDirection = direction;
380 cueDidChange();
381 }
382
383 void TextTrackCue::setSnapToLines(bool value)
384 {
385 if (m_snapToLines == value)
386 return;
387
388 cueWillChange();
389 m_snapToLines = value;
390 cueDidChange();
391 }
392
393 void TextTrackCue::setLine(int position, ExceptionState& exceptionState)
394 {
395 // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-ele ment.html#dom-texttrackcue-line
396 // On setting, if the text track cue snap-to-lines flag is not set, and the new
397 // value is negative or greater than 100, then throw an IndexSizeError excep tion.
398 if (!m_snapToLines && (position < 0 || position > 100)) {
399 exceptionState.throwDOMException(IndexSizeError, ExceptionMessages::fail edToSet("line", "TextTrackCue", "The snap-to-lines flag is not set, and the valu e provided (" + String::number(position) + ") is not between 0 and 100."));
400 return;
401 }
402
403 // Otherwise, set the text track cue line position to the new value.
404 if (m_linePosition == position)
405 return;
406
407 cueWillChange();
408 m_linePosition = position;
409 m_computedLinePosition = calculateComputedLinePosition();
410 cueDidChange();
411 }
412
413 void TextTrackCue::setPosition(int position, ExceptionState& exceptionState)
414 {
415 // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-ele ment.html#dom-texttrackcue-position
416 // On setting, if the new value is negative or greater than 100, then throw an IndexSizeError exception.
417 // Otherwise, set the text track cue text position to the new value.
418 if (isInvalidPercentage(position, "line", exceptionState))
419 return;
420
421 // Otherwise, set the text track cue line position to the new value.
422 if (m_textPosition == position)
423 return;
424
425 cueWillChange();
426 m_textPosition = position;
427 cueDidChange();
428 }
429
430 void TextTrackCue::setSize(int size, ExceptionState& exceptionState)
431 {
432 // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-ele ment.html#dom-texttrackcue-size
433 // On setting, if the new value is negative or greater than 100, then throw an IndexSizeError
434 // exception. Otherwise, set the text track cue size to the new value.
435 if (isInvalidPercentage(size, "line", exceptionState))
436 return;
437
438 // Otherwise, set the text track cue line position to the new value.
439 if (m_cueSize == size)
440 return;
441
442 cueWillChange();
443 m_cueSize = size;
444 cueDidChange();
445 }
446
447 const String& TextTrackCue::align() const
448 {
449 switch (m_cueAlignment) {
450 case Start:
451 return startKeyword();
452 case Middle:
453 return middleKeyword();
454 case End:
455 return endKeyword();
456 case Left:
457 return leftKeyword();
458 case Right:
459 return rightKeyword();
460 default:
461 ASSERT_NOT_REACHED();
462 return emptyString();
463 }
464 }
465
466 void TextTrackCue::setAlign(const String& value, ExceptionState& exceptionState)
467 {
468 // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-ele ment.html#dom-texttrackcue-align
469 // On setting, the text track cue alignment must be set to the value given i n the
470 // first cell of the row in the table above whose second cell is a case-sens itive
471 // match for the new value, if any. If none of the values match, then the us er
472 // agent must instead throw a SyntaxError exception.
473
474 CueAlignment alignment = m_cueAlignment;
475 if (value == startKeyword())
476 alignment = Start;
477 else if (value == middleKeyword())
478 alignment = Middle;
479 else if (value == endKeyword())
480 alignment = End;
481 else if (value == leftKeyword())
482 alignment = Left;
483 else if (value == rightKeyword())
484 alignment = Right;
485 else
486 exceptionState.throwDOMException(SyntaxError, ExceptionMessages::failedT oSet("align", "TextTrackCue", "The value provided ('" + value + "') is invalid. Only 'start', 'middle', 'end', 'left', and 'right' are accepted."));
487
488 if (alignment == m_cueAlignment)
489 return;
490
491 cueWillChange();
492 m_cueAlignment = alignment;
493 cueDidChange();
494 }
495
496 void TextTrackCue::setText(const String& text)
497 {
498 if (m_content == text)
499 return;
500
501 cueWillChange();
502 // Clear the document fragment but don't bother to create it again just yet as we can do that
503 // when it is requested.
504 m_webVTTNodeTree = 0;
505 m_content = text;
506 cueDidChange();
507 }
508
509 int TextTrackCue::cueIndex() 155 int TextTrackCue::cueIndex()
510 { 156 {
511 if (m_cueIndex == invalidCueIndex) 157 if (m_cueIndex == invalidCueIndex)
512 m_cueIndex = track()->cues()->getCueIndex(this); 158 m_cueIndex = track()->cues()->getCueIndex(this);
513 159
514 return m_cueIndex; 160 return m_cueIndex;
515 } 161 }
516 162
517 void TextTrackCue::invalidateCueIndex() 163 void TextTrackCue::invalidateCueIndex()
518 { 164 {
519 m_cueIndex = invalidCueIndex; 165 m_cueIndex = invalidCueIndex;
520 } 166 }
521 167
522 void TextTrackCue::createVTTNodeTree()
523 {
524 if (!m_webVTTNodeTree)
525 m_webVTTNodeTree = VTTParser::createDocumentFragmentFromCueText(document (), m_content);
526 }
527
528 void TextTrackCue::copyVTTNodeToDOMTree(ContainerNode* webVTTNode, ContainerNode * parent)
529 {
530 for (Node* node = webVTTNode->firstChild(); node; node = node->nextSibling() ) {
531 RefPtr<Node> clonedNode;
532 if (node->isVTTElement())
533 clonedNode = toVTTElement(node)->createEquivalentHTMLElement(documen t());
534 else
535 clonedNode = node->cloneNode(false);
536 parent->appendChild(clonedNode);
537 if (node->isContainerNode())
538 copyVTTNodeToDOMTree(toContainerNode(node), toContainerNode(clonedNo de));
539 }
540 }
541
542 PassRefPtr<DocumentFragment> TextTrackCue::getCueAsHTML()
543 {
544 createVTTNodeTree();
545 RefPtr<DocumentFragment> clonedFragment = DocumentFragment::create(document( ));
546 copyVTTNodeToDOMTree(m_webVTTNodeTree.get(), clonedFragment.get());
547 return clonedFragment.release();
548 }
549
550 PassRefPtr<DocumentFragment> TextTrackCue::createCueRenderingTree()
551 {
552 RefPtr<DocumentFragment> clonedFragment;
553 createVTTNodeTree();
554 clonedFragment = DocumentFragment::create(document());
555 m_webVTTNodeTree->cloneChildNodes(clonedFragment.get());
556 return clonedFragment.release();
557 }
558
559 bool TextTrackCue::dispatchEvent(PassRefPtr<Event> event) 168 bool TextTrackCue::dispatchEvent(PassRefPtr<Event> event)
560 { 169 {
561 // When a TextTrack's mode is disabled: no cues are active, no events fired. 170 // When a TextTrack's mode is disabled: no cues are active, no events fired.
562 if (!track() || track()->mode() == TextTrack::disabledKeyword()) 171 if (!track() || track()->mode() == TextTrack::disabledKeyword())
563 return false; 172 return false;
564 173
565 return EventTarget::dispatchEvent(event); 174 return EventTarget::dispatchEvent(event);
566 } 175 }
567 176
568 void TextTrackCue::setRegionId(const String& regionId)
569 {
570 if (m_regionId == regionId)
571 return;
572
573 cueWillChange();
574 m_regionId = regionId;
575 cueDidChange();
576 }
577
578 void TextTrackCue::notifyRegionWhenRemovingDisplayTree(bool notifyRegion)
579 {
580 m_notifyRegion = notifyRegion;
581 }
582
583 bool TextTrackCue::isActive() 177 bool TextTrackCue::isActive()
584 { 178 {
585 return m_isActive && track() && track()->mode() != TextTrack::disabledKeywor d(); 179 return m_isActive && track() && track()->mode() != TextTrack::disabledKeywor d();
586 } 180 }
587 181
588 void TextTrackCue::setIsActive(bool active) 182 void TextTrackCue::setIsActive(bool active)
589 { 183 {
590 m_isActive = active; 184 m_isActive = active;
591 185
592 // Remove the display tree as soon as the cue becomes inactive. 186 // Remove the display tree as soon as the cue becomes inactive.
593 if (!active) 187 if (!active)
594 removeDisplayTree(); 188 removeDisplayTree();
595 } 189 }
596 190
597 int TextTrackCue::calculateComputedLinePosition()
598 {
599 // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-ele ment.html#text-track-cue-computed-line-position
600
601 // If the text track cue line position is numeric, then that is the text
602 // track cue computed line position.
603 if (m_linePosition != undefinedPosition)
604 return m_linePosition;
605
606 // If the text track cue snap-to-lines flag of the text track cue is not
607 // set, the text track cue computed line position is the value 100;
608 if (!m_snapToLines)
609 return 100;
610
611 // Otherwise, it is the value returned by the following algorithm:
612
613 // If cue is not associated with a text track, return -1 and abort these
614 // steps.
615 if (!track())
616 return -1;
617
618 // Let n be the number of text tracks whose text track mode is showing or
619 // showing by default and that are in the media element's list of text
620 // tracks before track.
621 int n = track()->trackIndexRelativeToRenderedTracks();
622
623 // Increment n by one.
624 n++;
625
626 // Negate n.
627 n = -n;
628
629 return n;
630 }
631
632 static bool isCueParagraphSeparator(UChar character)
633 {
634 // Within a cue, paragraph boundaries are only denoted by Type B characters,
635 // such as U+000A LINE FEED (LF), U+0085 NEXT LINE (NEL), and U+2029 PARAGRA PH SEPARATOR.
636 return WTF::Unicode::category(character) & WTF::Unicode::Separator_Paragraph ;
637 }
638
639 void TextTrackCue::determineTextDirection()
640 {
641 DEFINE_STATIC_LOCAL(const String, rtTag, ("rt"));
642 createVTTNodeTree();
643
644 // Apply the Unicode Bidirectional Algorithm's Paragraph Level steps to the
645 // concatenation of the values of each WebVTT Text Object in nodes, in a
646 // pre-order, depth-first traversal, excluding WebVTT Ruby Text Objects and
647 // their descendants.
648 StringBuilder paragraphBuilder;
649 for (Node* node = m_webVTTNodeTree->firstChild(); node; node = NodeTraversal ::next(*node, m_webVTTNodeTree.get())) {
650 if (!node->isTextNode() || node->localName() == rtTag)
651 continue;
652
653 paragraphBuilder.append(node->nodeValue());
654 }
655
656 String paragraph = paragraphBuilder.toString();
657 if (!paragraph.length())
658 return;
659
660 for (size_t i = 0; i < paragraph.length(); ++i) {
661 UChar current = paragraph[i];
662 if (!current || isCueParagraphSeparator(current))
663 return;
664
665 if (UChar current = paragraph[i]) {
666 WTF::Unicode::Direction charDirection = WTF::Unicode::direction(curr ent);
667 if (charDirection == WTF::Unicode::LeftToRight) {
668 m_displayDirection = CSSValueLtr;
669 return;
670 }
671 if (charDirection == WTF::Unicode::RightToLeft
672 || charDirection == WTF::Unicode::RightToLeftArabic) {
673 m_displayDirection = CSSValueRtl;
674 return;
675 }
676 }
677 }
678 }
679
680 void TextTrackCue::calculateDisplayParameters()
681 {
682 // Steps 10.2, 10.3
683 determineTextDirection();
684
685 // 10.4 If the text track cue writing direction is horizontal, then let
686 // block-flow be 'tb'. Otherwise, if the text track cue writing direction is
687 // vertical growing left, then let block-flow be 'lr'. Otherwise, the text
688 // track cue writing direction is vertical growing right; let block-flow be
689 // 'rl'.
690
691 // The above step is done through the writing direction static map.
692
693 // 10.5 Determine the value of maximum size for cue as per the appropriate
694 // rules from the following list:
695 int maximumSize = m_textPosition;
696 if ((m_writingDirection == Horizontal && m_cueAlignment == Start && m_displa yDirection == CSSValueLtr)
697 || (m_writingDirection == Horizontal && m_cueAlignment == End && m_d isplayDirection == CSSValueRtl)
698 || (m_writingDirection == Horizontal && m_cueAlignment == Left)
699 || (m_writingDirection == VerticalGrowingLeft && (m_cueAlignment == Start || m_cueAlignment == Left))
700 || (m_writingDirection == VerticalGrowingRight && (m_cueAlignment == Start || m_cueAlignment == Left))) {
701 maximumSize = 100 - m_textPosition;
702 } else if ((m_writingDirection == Horizontal && m_cueAlignment == End && m_d isplayDirection == CSSValueLtr)
703 || (m_writingDirection == Horizontal && m_cueAlignment == Start && m _displayDirection == CSSValueRtl)
704 || (m_writingDirection == Horizontal && m_cueAlignment == Right)
705 || (m_writingDirection == VerticalGrowingLeft && (m_cueAlignment == End || m_cueAlignment == Right))
706 || (m_writingDirection == VerticalGrowingRight && (m_cueAlignment == End || m_cueAlignment == Right))) {
707 maximumSize = m_textPosition;
708 } else if (m_cueAlignment == Middle) {
709 maximumSize = m_textPosition <= 50 ? m_textPosition : (100 - m_textPosit ion);
710 maximumSize = maximumSize * 2;
711 } else {
712 ASSERT_NOT_REACHED();
713 }
714
715 // 10.6 If the text track cue size is less than maximum size, then let size
716 // be text track cue size. Otherwise, let size be maximum size.
717 m_displaySize = std::min(m_cueSize, maximumSize);
718
719 // FIXME: Understand why step 10.7 is missing (just a copy/paste error?)
720 // Could be done within a spec implementation check - http://crbug.com/30158 0
721
722 // 10.8 Determine the value of x-position or y-position for cue as per the
723 // appropriate rules from the following list:
724 if (m_writingDirection == Horizontal) {
725 switch (m_cueAlignment) {
726 case Start:
727 if (m_displayDirection == CSSValueLtr)
728 m_displayPosition.first = m_textPosition;
729 else
730 m_displayPosition.first = 100 - m_textPosition - m_displaySize;
731 break;
732 case End:
733 if (m_displayDirection == CSSValueRtl)
734 m_displayPosition.first = 100 - m_textPosition;
735 else
736 m_displayPosition.first = m_textPosition - m_displaySize;
737 break;
738 case Left:
739 if (m_displayDirection == CSSValueLtr)
740 m_displayPosition.first = m_textPosition;
741 else
742 m_displayPosition.first = 100 - m_textPosition;
743 break;
744 case Right:
745 if (m_displayDirection == CSSValueLtr)
746 m_displayPosition.first = m_textPosition - m_displaySize;
747 else
748 m_displayPosition.first = 100 - m_textPosition - m_displaySize;
749 break;
750 case Middle:
751 if (m_displayDirection == CSSValueLtr)
752 m_displayPosition.first = m_textPosition - m_displaySize / 2;
753 else
754 m_displayPosition.first = 100 - m_textPosition - m_displaySize / 2;
755 break;
756 case NumberOfAlignments:
757 ASSERT_NOT_REACHED();
758 }
759 } else {
760 // Cases for m_writingDirection being VerticalGrowing{Left|Right}
761 switch (m_cueAlignment) {
762 case Start:
763 case Left:
764 m_displayPosition.second = m_textPosition;
765 break;
766 case End:
767 case Right:
768 m_displayPosition.second = m_textPosition - m_displaySize;
769 break;
770 case Middle:
771 m_displayPosition.second = m_textPosition - m_displaySize / 2;
772 break;
773 case NumberOfAlignments:
774 ASSERT_NOT_REACHED();
775 }
776 }
777
778 // A text track cue has a text track cue computed line position whose value
779 // is defined in terms of the other aspects of the cue.
780 m_computedLinePosition = calculateComputedLinePosition();
781
782 // 10.9 Determine the value of whichever of x-position or y-position is not
783 // yet calculated for cue as per the appropriate rules from the following
784 // list:
785 if (m_snapToLines && m_displayPosition.second == undefinedPosition && m_writ ingDirection == Horizontal)
786 m_displayPosition.second = 0;
787
788 if (!m_snapToLines && m_displayPosition.second == undefinedPosition && m_wri tingDirection == Horizontal)
789 m_displayPosition.second = m_computedLinePosition;
790
791 if (m_snapToLines && m_displayPosition.first == undefinedPosition
792 && (m_writingDirection == VerticalGrowingLeft || m_writingDirection == VerticalGrowingRight))
793 m_displayPosition.first = 0;
794
795 if (!m_snapToLines && (m_writingDirection == VerticalGrowingLeft || m_writin gDirection == VerticalGrowingRight))
796 m_displayPosition.first = m_computedLinePosition;
797 }
798
799 void TextTrackCue::markFutureAndPastNodes(ContainerNode* root, double previousTi mestamp, double movieTime)
800 {
801 DEFINE_STATIC_LOCAL(const String, timestampTag, ("timestamp"));
802
803 bool isPastNode = true;
804 double currentTimestamp = previousTimestamp;
805 if (currentTimestamp > movieTime)
806 isPastNode = false;
807
808 for (Node* child = root->firstChild(); child; child = NodeTraversal::next(*c hild, root)) {
809 if (child->nodeName() == timestampTag) {
810 unsigned position = 0;
811 String timestamp = child->nodeValue();
812 double currentTimestamp = VTTParser::collectTimeStamp(timestamp, &po sition);
813 ASSERT(currentTimestamp != -1);
814
815 if (currentTimestamp > movieTime)
816 isPastNode = false;
817 }
818
819 if (child->isVTTElement()) {
820 toVTTElement(child)->setIsPastNode(isPastNode);
821 // Make an elemenet id match a cue id for style matching purposes.
822 if (!m_id.isEmpty())
823 toElement(child)->setIdAttribute(m_id);
824 }
825 }
826 }
827
828 void TextTrackCue::updateDisplayTree(double movieTime)
829 {
830 // The display tree may contain WebVTT timestamp objects representing
831 // timestamps (processing instructions), along with displayable nodes.
832
833 if (!track()->isRendered())
834 return;
835
836 // Clear the contents of the set.
837 m_cueBackgroundBox->removeChildren();
838
839 // Update the two sets containing past and future WebVTT objects.
840 RefPtr<DocumentFragment> referenceTree = createCueRenderingTree();
841 markFutureAndPastNodes(referenceTree.get(), startTime(), movieTime);
842 m_cueBackgroundBox->appendChild(referenceTree, ASSERT_NO_EXCEPTION);
843 }
844
845 PassRefPtr<TextTrackCueBox> TextTrackCue::getDisplayTree(const IntSize& videoSiz e)
846 {
847 RefPtr<TextTrackCueBox> displayTree = displayTreeInternal();
848 if (!m_displayTreeShouldChange || !track()->isRendered())
849 return displayTree;
850
851 // 10.1 - 10.10
852 calculateDisplayParameters();
853
854 // 10.11. Apply the terms of the CSS specifications to nodes within the
855 // following constraints, thus obtaining a set of CSS boxes positioned
856 // relative to an initial containing block:
857 displayTree->removeChildren();
858
859 // The document tree is the tree of WebVTT Node Objects rooted at nodes.
860
861 // The children of the nodes must be wrapped in an anonymous box whose
862 // 'display' property has the value 'inline'. This is the WebVTT cue
863 // background box.
864
865 // Note: This is contained by default in m_cueBackgroundBox.
866 m_cueBackgroundBox->setPart(cueShadowPseudoId());
867 displayTree->appendChild(m_cueBackgroundBox);
868
869 // FIXME(BUG 79916): Runs of children of WebVTT Ruby Objects that are not
870 // WebVTT Ruby Text Objects must be wrapped in anonymous boxes whose
871 // 'display' property has the value 'ruby-base'.
872
873 // FIXME(BUG 79916): Text runs must be wrapped according to the CSS
874 // line-wrapping rules, except that additionally, regardless of the value of
875 // the 'white-space' property, lines must be wrapped at the edge of their
876 // containing blocks, even if doing so requires splitting a word where there
877 // is no line breaking opportunity. (Thus, normally text wraps as needed,
878 // but if there is a particularly long word, it does not overflow as it
879 // normally would in CSS, it is instead forcibly wrapped at the box's edge.)
880 displayTree->applyCSSProperties(videoSize);
881
882 m_displayTreeShouldChange = false;
883
884 // 10.15. Let cue's text track cue display state have the CSS boxes in
885 // boxes.
886 return displayTree;
887 }
888
889 void TextTrackCue::removeDisplayTree()
890 {
891 if (m_notifyRegion && m_track->regions()) {
892 // The region needs to be informed about the cue removal.
893 VTTRegion* region = m_track->regions()->getRegionById(m_regionId);
894 if (region)
895 region->willRemoveTextTrackCueBox(m_displayTree.get());
896 }
897
898 displayTreeInternal()->remove(ASSERT_NO_EXCEPTION);
899 }
900
901 std::pair<double, double> TextTrackCue::getPositionCoordinates() const
902 {
903 // This method is used for setting x and y when snap to lines is not set.
904 std::pair<double, double> coordinates;
905
906 if (m_writingDirection == Horizontal && m_displayDirection == CSSValueLtr) {
907 coordinates.first = m_textPosition;
908 coordinates.second = m_computedLinePosition;
909
910 return coordinates;
911 }
912
913 if (m_writingDirection == Horizontal && m_displayDirection == CSSValueRtl) {
914 coordinates.first = 100 - m_textPosition;
915 coordinates.second = m_computedLinePosition;
916
917 return coordinates;
918 }
919
920 if (m_writingDirection == VerticalGrowingLeft) {
921 coordinates.first = 100 - m_computedLinePosition;
922 coordinates.second = m_textPosition;
923
924 return coordinates;
925 }
926
927 if (m_writingDirection == VerticalGrowingRight) {
928 coordinates.first = m_computedLinePosition;
929 coordinates.second = m_textPosition;
930
931 return coordinates;
932 }
933
934 ASSERT_NOT_REACHED();
935
936 return coordinates;
937 }
938
939 TextTrackCue::CueSetting TextTrackCue::settingName(const String& name)
940 {
941 DEFINE_STATIC_LOCAL(const String, verticalKeyword, ("vertical"));
942 DEFINE_STATIC_LOCAL(const String, lineKeyword, ("line"));
943 DEFINE_STATIC_LOCAL(const String, positionKeyword, ("position"));
944 DEFINE_STATIC_LOCAL(const String, sizeKeyword, ("size"));
945 DEFINE_STATIC_LOCAL(const String, alignKeyword, ("align"));
946 DEFINE_STATIC_LOCAL(const String, regionIdKeyword, ("region"));
947
948 if (name == verticalKeyword)
949 return Vertical;
950 else if (name == lineKeyword)
951 return Line;
952 else if (name == positionKeyword)
953 return Position;
954 else if (name == sizeKeyword)
955 return Size;
956 else if (name == alignKeyword)
957 return Align;
958 else if (RuntimeEnabledFeatures::webVTTRegionsEnabled() && name == regionIdK eyword)
959 return RegionId;
960
961 return None;
962 }
963
964 void TextTrackCue::parseSettings(const String& input)
965 {
966 unsigned position = 0;
967
968 while (position < input.length()) {
969
970 // The WebVTT cue settings part of a WebVTT cue consists of zero or more of the following components, in any order,
971 // separated from each other by one or more U+0020 SPACE characters or U +0009 CHARACTER TABULATION (tab) characters.
972 while (position < input.length() && VTTParser::isValidSettingDelimiter(i nput[position]))
973 position++;
974 if (position >= input.length())
975 break;
976
977 // When the user agent is to parse the WebVTT settings given by a string input for a text track cue cue,
978 // the user agent must run the following steps:
979 // 1. Let settings be the result of splitting input on spaces.
980 // 2. For each token setting in the list settings, run the following sub steps:
981 // 1. If setting does not contain a U+003A COLON character (:), or if the first U+003A COLON character (:)
982 // in setting is either the first or last character of setting, th en jump to the step labeled next setting.
983 unsigned endOfSetting = position;
984 String setting = VTTParser::collectWord(input, &endOfSetting);
985 CueSetting name;
986 size_t colonOffset = setting.find(':', 1);
987 if (colonOffset == kNotFound || !colonOffset || colonOffset == setting.l ength() - 1)
988 goto NextSetting;
989
990 // 2. Let name be the leading substring of setting up to and excluding t he first U+003A COLON character (:) in that string.
991 name = settingName(setting.substring(0, colonOffset));
992
993 // 3. Let value be the trailing substring of setting starting from the c haracter immediately after the first U+003A COLON character (:) in that string.
994 position += colonOffset + 1;
995 if (position >= input.length())
996 break;
997
998 // 4. Run the appropriate substeps that apply for the value of name, as follows:
999 switch (name) {
1000 case Vertical:
1001 {
1002 // If name is a case-sensitive match for "vertical"
1003 // 1. If value is a case-sensitive match for the string "rl", then l et cue's text track cue writing direction
1004 // be vertical growing left.
1005 String writingDirection = VTTParser::collectWord(input, &position);
1006 if (writingDirection == verticalGrowingLeftKeyword())
1007 m_writingDirection = VerticalGrowingLeft;
1008
1009 // 2. Otherwise, if value is a case-sensitive match for the string " lr", then let cue's text track cue writing
1010 // direction be vertical growing right.
1011 else if (writingDirection == verticalGrowingRightKeyword())
1012 m_writingDirection = VerticalGrowingRight;
1013 }
1014 break;
1015 case Line:
1016 {
1017 // 1-2 - Collect chars that are either '-', '%', or a digit.
1018 // 1. If value contains any characters other than U+002D HYPHEN-MINU S characters (-), U+0025 PERCENT SIGN
1019 // characters (%), and characters in the range U+0030 DIGIT ZERO (0) to U+0039 DIGIT NINE (9), then jump
1020 // to the step labeled next setting.
1021 StringBuilder linePositionBuilder;
1022 while (position < input.length() && (input[position] == '-' || input [position] == '%' || isASCIIDigit(input[position])))
1023 linePositionBuilder.append(input[position++]);
1024 if (position < input.length() && !VTTParser::isValidSettingDelimiter (input[position]))
1025 break;
1026
1027 // 2. If value does not contain at least one character in the range U+0030 DIGIT ZERO (0) to U+0039 DIGIT
1028 // NINE (9), then jump to the step labeled next setting.
1029 // 3. If any character in value other than the first character is a U+002D HYPHEN-MINUS character (-), then
1030 // jump to the step labeled next setting.
1031 // 4. If any character in value other than the last character is a U +0025 PERCENT SIGN character (%), then
1032 // jump to the step labeled next setting.
1033 String linePosition = linePositionBuilder.toString();
1034 if (linePosition.find('-', 1) != kNotFound || linePosition.reverseFi nd("%", linePosition.length() - 2) != kNotFound)
1035 break;
1036
1037 // 5. If the first character in value is a U+002D HYPHEN-MINUS chara cter (-) and the last character in value is a
1038 // U+0025 PERCENT SIGN character (%), then jump to the step label ed next setting.
1039 if (linePosition[0] == '-' && linePosition[linePosition.length() - 1 ] == '%')
1040 break;
1041
1042 // 6. Ignoring the trailing percent sign, if any, interpret value as a (potentially signed) integer, and
1043 // let number be that number.
1044 // NOTE: toInt ignores trailing non-digit characters, such as '%'.
1045 bool validNumber;
1046 int number = linePosition.toInt(&validNumber);
1047 if (!validNumber)
1048 break;
1049
1050 // 7. If the last character in value is a U+0025 PERCENT SIGN charac ter (%), but number is not in the range
1051 // 0 ≤ number ≤ 100, then jump to the step labeled next setting.
1052 // 8. Let cue's text track cue line position be number.
1053 // 9. If the last character in value is a U+0025 PERCENT SIGN charac ter (%), then let cue's text track cue
1054 // snap-to-lines flag be false. Otherwise, let it be true.
1055 if (linePosition[linePosition.length() - 1] == '%') {
1056 if (number < 0 || number > 100)
1057 break;
1058
1059 // 10 - If '%' then set snap-to-lines flag to false.
1060 m_snapToLines = false;
1061 }
1062
1063 m_linePosition = number;
1064 }
1065 break;
1066 case Position:
1067 {
1068 // 1. If value contains any characters other than U+0025 PERCENT SIG N characters (%) and characters in the range
1069 // U+0030 DIGIT ZERO (0) to U+0039 DIGIT NINE (9), then jump to t he step labeled next setting.
1070 // 2. If value does not contain at least one character in the range U+0030 DIGIT ZERO (0) to U+0039 DIGIT NINE (9),
1071 // then jump to the step labeled next setting.
1072 String textPosition = VTTParser::collectDigits(input, &position);
1073 if (textPosition.isEmpty())
1074 break;
1075 if (position >= input.length())
1076 break;
1077
1078 // 3. If any character in value other than the last character is a U +0025 PERCENT SIGN character (%), then jump
1079 // to the step labeled next setting.
1080 // 4. If the last character in value is not a U+0025 PERCENT SIGN ch aracter (%), then jump to the step labeled
1081 // next setting.
1082 if (input[position++] != '%')
1083 break;
1084 if (position < input.length() && !VTTParser::isValidSettingDelimiter (input[position]))
1085 break;
1086
1087 // 5. Ignoring the trailing percent sign, interpret value as an inte ger, and let number be that number.
1088 // 6. If number is not in the range 0 ≤ number ≤ 100, then jump to t he step labeled next setting.
1089 // NOTE: toInt ignores trailing non-digit characters, such as '%'.
1090 bool validNumber;
1091 int number = textPosition.toInt(&validNumber);
1092 if (!validNumber)
1093 break;
1094 if (number < 0 || number > 100)
1095 break;
1096
1097 // 7. Let cue's text track cue text position be number.
1098 m_textPosition = number;
1099 }
1100 break;
1101 case Size:
1102 {
1103 // 1. If value contains any characters other than U+0025 PERCENT SIG N characters (%) and characters in the
1104 // range U+0030 DIGIT ZERO (0) to U+0039 DIGIT NINE (9), then jum p to the step labeled next setting.
1105 // 2. If value does not contain at least one character in the range U+0030 DIGIT ZERO (0) to U+0039 DIGIT
1106 // NINE (9), then jump to the step labeled next setting.
1107 String cueSize = VTTParser::collectDigits(input, &position);
1108 if (cueSize.isEmpty())
1109 break;
1110 if (position >= input.length())
1111 break;
1112
1113 // 3. If any character in value other than the last character is a U +0025 PERCENT SIGN character (%),
1114 // then jump to the step labeled next setting.
1115 // 4. If the last character in value is not a U+0025 PERCENT SIGN ch aracter (%), then jump to the step
1116 // labeled next setting.
1117 if (input[position++] != '%')
1118 break;
1119 if (position < input.length() && !VTTParser::isValidSettingDelimiter (input[position]))
1120 break;
1121
1122 // 5. Ignoring the trailing percent sign, interpret value as an inte ger, and let number be that number.
1123 // 6. If number is not in the range 0 ≤ number ≤ 100, then jump to t he step labeled next setting.
1124 bool validNumber;
1125 int number = cueSize.toInt(&validNumber);
1126 if (!validNumber)
1127 break;
1128 if (number < 0 || number > 100)
1129 break;
1130
1131 // 7. Let cue's text track cue size be number.
1132 m_cueSize = number;
1133 }
1134 break;
1135 case Align:
1136 {
1137 String cueAlignment = VTTParser::collectWord(input, &position);
1138
1139 // 1. If value is a case-sensitive match for the string "start", the n let cue's text track cue alignment be start alignment.
1140 if (cueAlignment == startKeyword())
1141 m_cueAlignment = Start;
1142
1143 // 2. If value is a case-sensitive match for the string "middle", th en let cue's text track cue alignment be middle alignment.
1144 else if (cueAlignment == middleKeyword())
1145 m_cueAlignment = Middle;
1146
1147 // 3. If value is a case-sensitive match for the string "end", then let cue's text track cue alignment be end alignment.
1148 else if (cueAlignment == endKeyword())
1149 m_cueAlignment = End;
1150
1151 // 4. If value is a case-sensitive match for the string "left", then let cue's text track cue alignment be left alignment.
1152 else if (cueAlignment == leftKeyword())
1153 m_cueAlignment = Left;
1154
1155 // 5. If value is a case-sensitive match for the string "right", the n let cue's text track cue alignment be right alignment.
1156 else if (cueAlignment == rightKeyword())
1157 m_cueAlignment = Right;
1158 }
1159 break;
1160 case RegionId:
1161 m_regionId = VTTParser::collectWord(input, &position);
1162 break;
1163 case None:
1164 break;
1165 }
1166
1167 NextSetting:
1168 position = endOfSetting;
1169 }
1170
1171 // If cue's line position is not auto or cue's size is not 100 or cue's
1172 // writing direction is not horizontal, but cue's region identifier is not
1173 // the empty string, let cue's region identifier be the empty string.
1174 if (m_regionId.isEmpty())
1175 return;
1176
1177 if (m_linePosition != undefinedPosition || m_cueSize != 100 || m_writingDire ction != Horizontal)
1178 m_regionId = emptyString();
1179 }
1180
1181 CSSValueID TextTrackCue::getCSSAlignment() const
1182 {
1183 return displayAlignmentMap[m_cueAlignment];
1184 }
1185
1186 CSSValueID TextTrackCue::getCSSWritingDirection() const
1187 {
1188 return m_displayDirection;
1189 }
1190
1191 CSSValueID TextTrackCue::getCSSWritingMode() const
1192 {
1193 return displayWritingModeMap[m_writingDirection];
1194 }
1195
1196 int TextTrackCue::getCSSSize() const
1197 {
1198 return m_displaySize;
1199 }
1200
1201 std::pair<double, double> TextTrackCue::getCSSPosition() const
1202 {
1203 if (!m_snapToLines)
1204 return getPositionCoordinates();
1205
1206 return m_displayPosition;
1207 }
1208
1209 const AtomicString& TextTrackCue::interfaceName() const 191 const AtomicString& TextTrackCue::interfaceName() const
1210 { 192 {
1211 return EventTargetNames::TextTrackCue; 193 return EventTargetNames::TextTrackCue;
1212 } 194 }
1213 195
1214 ExecutionContext* TextTrackCue::executionContext() const
1215 {
1216 ASSERT(m_cueBackgroundBox);
1217 return m_cueBackgroundBox->executionContext();
1218 }
1219
1220 Document& TextTrackCue::document() const
1221 {
1222 ASSERT(m_cueBackgroundBox);
1223 return m_cueBackgroundBox->document();
1224 }
1225
1226 } // namespace WebCore 196 } // namespace WebCore
OLDNEW
« no previous file with comments | « Source/core/html/track/TextTrackCue.h ('k') | Source/core/html/track/vtt/VTTCue.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698