bdc4dfa0d1ef75fe6a0509c328fc5488b3c189ff
[WebKit-https.git] / Source / WebCore / html / track / LoadableTextTrack.cpp
1 /*
2  * Copyright (C) 2011, 2013 Google Inc.  All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
17  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24  */
25
26 #include "config.h"
27
28 #if ENABLE(VIDEO_TRACK)
29
30 #include "LoadableTextTrack.h"
31
32 #include "Event.h"
33 #include "HTMLTrackElement.h"
34 #include "ScriptExecutionContext.h"
35 #include "TextTrackCueList.h"
36
37 #if ENABLE(WEBVTT_REGIONS)
38 #include "VTTRegionList.h"
39 #endif
40
41 namespace WebCore {
42
43 LoadableTextTrack::LoadableTextTrack(HTMLTrackElement* track, const String& kind, const String& label, const String& language)
44     : TextTrack(&track->document(), track, kind, emptyString(), label, language, TrackElement)
45     , m_trackElement(track)
46     , m_loadTimer(this, &LoadableTextTrack::loadTimerFired)
47     , m_isDefault(false)
48 {
49 }
50
51 LoadableTextTrack::~LoadableTextTrack()
52 {
53 }
54
55 void LoadableTextTrack::clearClient()
56 {
57     m_trackElement = 0;
58     TextTrack::clearClient();
59 }
60
61 void LoadableTextTrack::scheduleLoad(const URL& url)
62 {
63     if (url == m_url)
64         return;
65
66     // 4.8.10.12.3 Sourcing out-of-band text tracks (continued)
67
68     // 2. Let URL be the track URL of the track element.
69     m_url = url;
70     
71     // 3. Asynchronously run the remaining steps, while continuing with whatever task 
72     // was responsible for creating the text track or changing the text track mode.
73     if (!m_loadTimer.isActive())
74         m_loadTimer.startOneShot(0);
75 }
76
77 Element* LoadableTextTrack::element()
78 {
79     return m_trackElement;
80 }
81     
82 void LoadableTextTrack::setTrackElement(HTMLTrackElement* element)
83 {
84     ASSERT(!m_trackElement || m_trackElement == element);
85     m_trackElement = element;
86 }
87
88 void LoadableTextTrack::loadTimerFired(Timer&)
89 {
90     if (m_loader)
91         m_loader->cancelLoad();
92
93     if (!m_trackElement)
94         return;
95
96     // 4.8.10.12.3 Sourcing out-of-band text tracks (continued)
97
98     // 4. Download: If URL is not the empty string, perform a potentially CORS-enabled fetch of URL, with the
99     // mode being the state of the media element's crossorigin content attribute, the origin being the
100     // origin of the media element's Document, and the default origin behaviour set to fail.
101     m_loader = std::make_unique<TextTrackLoader>(static_cast<TextTrackLoaderClient&>(*this), static_cast<ScriptExecutionContext*>(&m_trackElement->document()));
102     if (!m_loader->load(m_url, m_trackElement->mediaElementCrossOriginAttribute()))
103         m_trackElement->didCompleteLoad(HTMLTrackElement::Failure);
104 }
105
106 void LoadableTextTrack::newCuesAvailable(TextTrackLoader* loader)
107 {
108     ASSERT_UNUSED(loader, m_loader.get() == loader);
109
110     Vector<RefPtr<TextTrackCue>> newCues;
111     m_loader->getNewCues(newCues);
112
113     if (!m_cues)
114         m_cues = TextTrackCueList::create();    
115
116     for (size_t i = 0; i < newCues.size(); ++i) {
117         newCues[i]->setTrack(this);
118         m_cues->add(newCues[i]);
119     }
120
121     if (client())
122         client()->textTrackAddCues(this, m_cues.get());
123 }
124
125 void LoadableTextTrack::cueLoadingCompleted(TextTrackLoader* loader, bool loadingFailed)
126 {
127     ASSERT_UNUSED(loader, m_loader.get() == loader);
128
129     if (!m_trackElement)
130         return;
131
132     m_trackElement->didCompleteLoad(loadingFailed ? HTMLTrackElement::Failure : HTMLTrackElement::Success);
133 }
134
135 #if ENABLE(WEBVTT_REGIONS)
136 void LoadableTextTrack::newRegionsAvailable(TextTrackLoader* loader)
137 {
138     ASSERT_UNUSED(loader, m_loader.get() == loader);
139
140     Vector<RefPtr<VTTRegion>> newRegions;
141     m_loader->getNewRegions(newRegions);
142
143     for (size_t i = 0; i < newRegions.size(); ++i) {
144         newRegions[i]->setTrack(this);
145         regions()->add(newRegions[i]);
146     }
147 }
148 #endif
149
150 AtomicString LoadableTextTrack::id() const
151 {
152     if (m_trackElement)
153         return m_trackElement->getAttribute("id");
154     return emptyString();
155 }
156
157 size_t LoadableTextTrack::trackElementIndex()
158 {
159     ASSERT(m_trackElement);
160     ASSERT(m_trackElement->parentNode());
161
162     size_t index = 0;
163     for (Node* node = m_trackElement->parentNode()->firstChild(); node; node = node->nextSibling()) {
164         if (!node->hasTagName(trackTag) || !node->parentNode())
165             continue;
166         if (node == m_trackElement)
167             return index;
168         ++index;
169     }
170     ASSERT_NOT_REACHED();
171
172     return 0;
173 }
174
175 } // namespace WebCore
176
177 #endif